diff options
Diffstat (limited to 'src/de/lmu/ifi/dbs/elki/database/ids')
27 files changed, 676 insertions, 115 deletions
diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/ArrayDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/ArrayDBIDs.java index 13d6ea58..68bbb83d 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/ArrayDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/ArrayDBIDs.java @@ -42,6 +42,7 @@ public interface ArrayDBIDs extends DBIDs { * * @return Iterator */ + @Override public DBIDIter iter(); /** @@ -49,6 +50,7 @@ public interface ArrayDBIDs extends DBIDs { * * @return size */ + @Override public int size(); /** @@ -61,5 +63,5 @@ public interface ArrayDBIDs extends DBIDs { * @param key Key to search for * @return Offset of key */ - public int binarySearch(DBID key); + public int binarySearch(DBIDRef key); } diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/ArrayModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/ArrayModifiableDBIDs.java index e9a6c8e0..95bcc2f7 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/ArrayModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/ArrayModifiableDBIDs.java @@ -59,4 +59,12 @@ public interface ArrayModifiableDBIDs extends ModifiableDBIDs, ArrayDBIDs { * @return previous value */ public DBID set(int i, DBID newval); + + /** + * Swap DBIDs add positions a and b. + * + * @param a First position + * @param b Second position + */ + public void swap(int a, int b); }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBID.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBID.java index 1391b75b..8d98893d 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBID.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBID.java @@ -37,11 +37,67 @@ package de.lmu.ifi.dbs.elki.database.ids; * * @apiviz.landmark */ -public interface DBID extends Comparable<DBID>, ArrayDBIDs { +public interface DBID extends DBIDRef, Comparable<DBIDRef>, ArrayDBIDs { /** - * Return the integer value of the object ID, if possible. + * Compare the <em>current</em> value of two referenced DBIDs. * - * @return integer id + * @param other Other DBID reference (or DBID) + * @return {@code true} when the references <em>currently</em> refer to the same. */ - public int getIntegerID(); + @Override + public boolean sameDBID(DBIDRef other); + + /** + * Compare two objects by the value of the referenced DBID. + * + * @param other Other DBID or object + * @return -1, 0 or +1 + */ + @Override + public int compareDBID(DBIDRef other); + + /** + * In contrast to {@link DBIDRef}, the DBID interface is supposed to have a + * stable hash code. However, it is generally preferred to use optimized + * storage classes instead of Java collections! + * + * @return hash code + */ + @Override + public int hashCode(); + + /** + * In contrast to {@link DBIDRef}, the DBID interface is supposed to have a + * stable equals for other DBIDs. + * + * Yet, {@link #sameDBID} is more type safe and explicit. + * + * @return true when the object is the same DBID. + */ + @Override + public boolean equals(Object obj); + + /** + * Part of the DBIDRef API, this <em>must</em> return {@code this} for an + * actual DBID. + * + * @return {@code this} + * @deprecated When the object is known to be a DBID, the usage of this method + * is pointless, therefore it is marked as deprecated to cause a + * warning. + */ + @Deprecated + @Override + public DBID getDBID(); + + /** + * Compare two DBIDs for ordering. + * + * Consider using {@link #compareDBID}, which is more explicit. + * + * @param other Other DBID object + * @return Comparison result + */ + @Override + public int compareTo(DBIDRef other); }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDFactory.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDFactory.java index f35f390b..6063508b 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDFactory.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDFactory.java @@ -40,7 +40,7 @@ import de.lmu.ifi.dbs.elki.persistent.FixedSizeByteBufferSerializer; * @apiviz.uses DBIDRange oneway - - «create» * @apiviz.uses ArrayModifiableDBIDs oneway - - «create» * @apiviz.uses HashSetModifiableDBIDs oneway - - «create» - * @apiviz.uses TreeSetModifiableDBIDs oneway - - «create» + * @apiviz.uses HashSetModifiableDBIDs oneway - - «create» * @apiviz.has ByteBufferSerializer oneway - - provides */ public interface DBIDFactory { @@ -89,12 +89,12 @@ public interface DBIDFactory { /** * Make a DBID pair from two existing DBIDs. * - * @param first first DBID - * @param second second DBID + * @param id1 first DBID + * @param id2 second DBID * * @return new pair. */ - public DBIDPair makePair(DBID first, DBID second); + public DBIDPair makePair(DBIDRef id1, DBIDRef id2); /** * Make a new (modifiable) array of DBIDs. diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDIter.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDIter.java index a41284f4..f2d0ae91 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDIter.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDIter.java @@ -22,6 +22,9 @@ package de.lmu.ifi.dbs.elki.database.ids; You should have received a copy of the GNU Affero General Public License along with this program. If not, see <http://www.gnu.org/licenses/>. */ + +import de.lmu.ifi.dbs.elki.utilities.iterator.Iter; + /** * Iterator for DBIDs. * @@ -30,11 +33,15 @@ package de.lmu.ifi.dbs.elki.database.ids; * with Java, but at the same time, the syntax is much more compatible with for * loops. * - * Usage example: <blockquote><code>{@code + * Usage example: + * + * <pre> + * {@code * for (DBIDIter iter = ids.iter(); iter.valid(); iter.advance()) { * iter.getDBID(); * } - * }</code></blockquote> + * } + * </pre> * * We list some fundamental differences. * <ul> @@ -47,33 +54,15 @@ package de.lmu.ifi.dbs.elki.database.ids; * * @author Erich Schubert */ -public interface DBIDIter { - /** - * Returns true if the iterator currently points to a valid object. - * - * @return a <code>boolean</code> value - */ - public boolean valid(); - +public interface DBIDIter extends DBIDRef, Iter { /** - * Moves the iterator forward to the next entry. + * Get the referenced {@link DBID}. * - * @throws java.util.NoSuchElementException if the iterator is already - * exhausted - */ - public void advance(); - - /** - * Return the integer value of the object ID, if possible. - * - * @return integer id - */ - public int getIntegerID(); - - /** - * Get the current DBID. + * Efficiency note: this may require materialization of a DBID object - if + * possible, use DBIDRef based APIs instead. * - * @return current DBID + * @return referenced DBID */ + @Override public DBID getDBID(); }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDMIter.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDMIter.java new file mode 100644 index 00000000..fe3b182c --- /dev/null +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDMIter.java @@ -0,0 +1,38 @@ +package de.lmu.ifi.dbs.elki.database.ids; +/* + This file is part of ELKI: + Environment for Developing KDD-Applications Supported by Index-Structures + + Copyright (C) 2012 + Ludwig-Maximilians-Universität München + Lehr- und Forschungseinheit für Datenbanksysteme + ELKI Development Team + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/** + * Modifiable DBID iterator. + * + * @author Erich Schubert + */ +public interface DBIDMIter extends DBIDIter { + /** + * Remove the object the iterator currently points to. + * + * Subsequent calls to {@link #getDBID} may return a different element. + * Call {@link #advance()} to advance the iterator to the next element for further processing. + */ + void remove(); +} diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRange.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRange.java index 48a1f0ba..1b9ccc3b 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRange.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRange.java @@ -23,7 +23,6 @@ package de.lmu.ifi.dbs.elki.database.ids; along with this program. If not, see <http://www.gnu.org/licenses/>. */ - /** * Static DBID range. * @@ -39,5 +38,5 @@ public interface DBIDRange extends ArrayStaticDBIDs { * @param dbid ID to compute index for * @return index */ - public int getOffset(DBID dbid); + public int getOffset(DBIDRef dbid); }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRef.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRef.java new file mode 100644 index 00000000..0934b10b --- /dev/null +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDRef.java @@ -0,0 +1,92 @@ +package de.lmu.ifi.dbs.elki.database.ids; + +/* + This file is part of ELKI: + Environment for Developing KDD-Applications Supported by Index-Structures + + Copyright (C) 2012 + Ludwig-Maximilians-Universität München + Lehr- und Forschungseinheit für Datenbanksysteme + ELKI Development Team + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/** + * Some object referencing a {@link DBID}. Could be a {@link DBID}, a + * {@link DBIDIter}, for example. + * + * Important note: <em>do not assume this reference to be stable</em>. Iterators + * are a good example how the DBIDRef may change. + * + * @author Erich Schubert + */ +public interface DBIDRef { + /** + * Get the referenced {@link DBID}. + * + * Efficiency note: this may require materialization of a DBID object. + * + * @return referenced DBID + */ + public DBID getDBID(); + + /** + * Return the integer value of the object ID, if possible. + * + * @return integer id + */ + public int getIntegerID(); + + /** + * WARNING: Hash codes of this interface <b>might not be stable</b> (e.g. for + * iterators). + * + * @return current hash code (<b>may change!</b>) + * + * @deprecated Do not use this hash code. Some implementations will not offer + * stable hash codes! + */ + @Override + @Deprecated + public int hashCode(); + + /** + * WARNING: calling equality on a reference may be an indicator of incorrect + * usage, as it is not clear whether the programmer meant the references to be + * the same or the DBIDs. + * + * @param obj Object to compare with + * @return True when they are the same object + */ + @Override + @Deprecated + public boolean equals(Object obj); + + /** + * Compare the <em>current</em> value of two referenced DBIDs. + * + * @param other Other DBID reference (or DBID) + * @return {@code true} when the references <em>currently</em> refer to the same. + */ + public boolean sameDBID(DBIDRef other); + + /** + * Compare two objects by the value of the referenced DBID. + * + * @param other Other DBID or object + * @return -1, 0 or +1 + */ + public int compareDBID(DBIDRef other); +}
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDUtil.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDUtil.java index cd2bd4e0..000659b9 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDUtil.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDUtil.java @@ -25,6 +25,7 @@ package de.lmu.ifi.dbs.elki.database.ids; import java.util.Random; +import de.lmu.ifi.dbs.elki.database.ids.generic.UnmodifiableArrayDBIDs; import de.lmu.ifi.dbs.elki.database.ids.generic.UnmodifiableDBIDs; import de.lmu.ifi.dbs.elki.persistent.ByteBufferSerializer; @@ -185,15 +186,45 @@ public final class DBIDUtil { return intersection(second, first); } ModifiableDBIDs inter = newHashSet(first.size()); - for(DBID id : first) { - if(second.contains(id)) { - inter.add(id); + for(DBIDIter it = first.iter(); it.valid(); it.advance()) { + if(second.contains(it)) { + inter.add(it); } } return inter; } /** + * Compute the set symmetric intersection of two sets. + * + * @param first First set + * @param second Second set + * @param firstonly OUTPUT: elements only in first. MUST BE EMPTY + * @param intersection OUTPUT: elements in intersection. MUST BE EMPTY + * @param secondonly OUTPUT: elements only in second. MUST BE EMPTY + */ + // TODO: optimize? + public static void symmetricIntersection(DBIDs first, DBIDs second, HashSetModifiableDBIDs firstonly, HashSetModifiableDBIDs intersection, HashSetModifiableDBIDs secondonly) { + if(first.size() > second.size()) { + symmetricIntersection(second, first, secondonly, intersection, firstonly); + return; + } + assert(firstonly.size() == 0) : "OUTPUT set should be empty!"; + assert(intersection.size() == 0) : "OUTPUT set should be empty!"; + assert(secondonly.size() == 0) : "OUTPUT set should be empty!"; + // Initialize with second + secondonly.addDBIDs(second); + for(DBIDIter it = first.iter(); it.valid(); it.advance()) { + // Try to remove + if(secondonly.remove(it)) { + intersection.add(it); + } else { + firstonly.add(it); + } + } + } + + /** * Returns the union of the two specified collection of IDs. * * @param ids1 the first collection @@ -201,7 +232,7 @@ public final class DBIDUtil { * @return the union of ids1 and ids2 without duplicates */ public static ModifiableDBIDs union(DBIDs ids1, DBIDs ids2) { - ModifiableDBIDs result = DBIDUtil.newHashSet(); + ModifiableDBIDs result = DBIDUtil.newHashSet(Math.max(ids1.size(), ids2.size())); result.addDBIDs(ids1); result.addDBIDs(ids2); return result; @@ -215,8 +246,7 @@ public final class DBIDUtil { * @return the difference of ids1 minus ids2 */ public static ModifiableDBIDs difference(DBIDs ids1, DBIDs ids2) { - ModifiableDBIDs result = DBIDUtil.newHashSet(); - result.addDBIDs(ids1); + ModifiableDBIDs result = DBIDUtil.newHashSet(ids1); result.removeDBIDs(ids2); return result; } @@ -231,7 +261,11 @@ public final class DBIDUtil { if(existing instanceof StaticDBIDs) { return (StaticDBIDs) existing; } - return new UnmodifiableDBIDs(existing); + if (existing instanceof ArrayDBIDs) { + return new UnmodifiableArrayDBIDs((ArrayDBIDs)existing); + } else { + return new UnmodifiableDBIDs(existing); + } } /** @@ -293,7 +327,7 @@ public final class DBIDUtil { * * @return DBID pair */ - public static DBIDPair newPair(DBID id1, DBID id2) { + public static DBIDPair newPair(DBIDRef id1, DBIDRef id2) { return DBIDFactory.FACTORY.makePair(id1, id2); } @@ -319,7 +353,7 @@ public final class DBIDUtil { */ public static ModifiableDBIDs randomSample(DBIDs source, int k, Long seed) { if(k <= 0 || k > source.size()) { - throw new IllegalArgumentException("Illegal value for size of random sample: " + k); + throw new IllegalArgumentException("Illegal value for size of random sample: " + k+ " > "+source.size()+" or < 0"); } final Random random; if(seed != null) { diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDs.java index ef83ba69..e9a3e0ab 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/DBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/DBIDs.java @@ -32,18 +32,21 @@ import java.util.Iterator; * * @apiviz.landmark * @apiviz.composedOf DBID + * @apiviz.has DBIDIter */ public interface DBIDs extends Iterable<DBID> { /** - * Retrieve Iterator access to the IDs. + * Get a DBID iterator (a more efficient API). * - * @return an iterator for the IDs - */ - @Override - public Iterator<DBID> iterator(); - - /** - * Get a DBIDIterator (a more efficient API). + * usage example: + * + * <pre> + * {@code + * for(DBIDIter iter = ids.iter(); iter.valid(); iter.advance()) { + * DBID id = iter.getDBID(); + * } + * } + * </pre> * * @return iterator */ @@ -62,7 +65,7 @@ public interface DBIDs extends Iterable<DBID> { * @param o object to test * @return true when contained */ - public boolean contains(DBID o); + public boolean contains(DBIDRef o); /** * Test for an empty DBID collection. @@ -70,4 +73,13 @@ public interface DBIDs extends Iterable<DBID> { * @return true when empty. */ public boolean isEmpty(); + + /** + * Classic iterator. + * + * @deprecated Use {@link DBIDIter} API instead. + */ + @Override + @Deprecated + public Iterator<DBID> iterator(); } diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/EmptyDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/EmptyDBIDs.java index 5a7d6991..a85b8954 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/EmptyDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/EmptyDBIDs.java @@ -26,12 +26,15 @@ package de.lmu.ifi.dbs.elki.database.ids; import java.util.Iterator; import java.util.NoSuchElementException; +import de.lmu.ifi.dbs.elki.logging.LoggingUtil; import de.lmu.ifi.dbs.elki.utilities.iterator.EmptyIterator; /** * Empty DBID collection. * * @author Erich Schubert + * + * @apiviz.composedOf EmptyDBIDIterator */ public class EmptyDBIDs implements ArrayStaticDBIDs, SetDBIDs { /** @@ -47,7 +50,7 @@ public class EmptyDBIDs implements ArrayStaticDBIDs, SetDBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return false; } @@ -77,7 +80,7 @@ public class EmptyDBIDs implements ArrayStaticDBIDs, SetDBIDs { } @Override - public int binarySearch(DBID key) { + public int binarySearch(DBIDRef key) { return -1; // Not found } @@ -106,5 +109,23 @@ public class EmptyDBIDs implements ArrayStaticDBIDs, SetDBIDs { public DBID getDBID() { throw new NoSuchElementException(); } + + @Override + public boolean equals(Object other) { + if (other instanceof DBID) { + LoggingUtil.warning("Programming error detected: DBIDItr.equals(DBID). Use sameDBID()!", new Throwable()); + } + return super.equals(other); + } + + @Override + public boolean sameDBID(DBIDRef other) { + return false; + } + + @Override + public int compareDBID(DBIDRef other) { + throw new UnsupportedOperationException("Invalid iterator position. Cannot compare."); + } } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/ModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/ModifiableDBIDs.java index 97646902..c92caef0 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/ModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/ModifiableDBIDs.java @@ -54,17 +54,36 @@ public interface ModifiableDBIDs extends DBIDs { * * @param id ID to add */ - boolean add(DBID id); + boolean add(DBIDRef id); /** * Remove a single DBID from the collection. * * @param id ID to remove */ - boolean remove(DBID id); + boolean remove(DBIDRef id); /** * Clear this collection. */ void clear(); + + /** + * Get a <em>modifiable</em> DBID iterator (a more efficient API). + * + * usage example: + * + * <pre> + * {@code + * for(DBIDMIter iter = ids.iter(); iter.valid(); iter.advance()) { + * DBID id = iter.getDBID(); + * iter.remove(); + * } + * } + * </pre> + * + * @return modifiable iterator + */ + @Override + DBIDMIter iter(); }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/DBIDIterAdapter.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/DBIDIterAdapter.java index c517ea9f..91e307c2 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/DBIDIterAdapter.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/DBIDIterAdapter.java @@ -1,10 +1,5 @@ package de.lmu.ifi.dbs.elki.database.ids.generic; -import java.util.Iterator; - -import de.lmu.ifi.dbs.elki.database.ids.DBID; -import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; - /* This file is part of ELKI: Environment for Developing KDD-Applications Supported by Index-Structures @@ -28,12 +23,18 @@ import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; along with this program. If not, see <http://www.gnu.org/licenses/>. */ +import java.util.Iterator; + +import de.lmu.ifi.dbs.elki.database.ids.DBID; +import de.lmu.ifi.dbs.elki.database.ids.DBIDMIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; + /** * Iterator for classic collections. * * @author Erich Schubert */ -public class DBIDIterAdapter implements DBIDIter { +public class DBIDIterAdapter implements DBIDMIter { /** * Current DBID */ @@ -79,4 +80,21 @@ public class DBIDIterAdapter implements DBIDIter { public DBID getDBID() { return cur; } + + @Override + public void remove() { + iter.remove(); + } + + @Override + public boolean sameDBID(DBIDRef other) { + return cur.getIntegerID() == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + final int thisVal = cur.getIntegerID(); + final int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericArrayModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericArrayModifiableDBIDs.java index f271180d..f02c5064 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericArrayModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericArrayModifiableDBIDs.java @@ -30,6 +30,8 @@ import java.util.Comparator; import de.lmu.ifi.dbs.elki.database.ids.ArrayModifiableDBIDs; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDMIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; /** @@ -80,7 +82,7 @@ public class GenericArrayModifiableDBIDs extends ArrayList<DBID> implements Arra public boolean addDBIDs(DBIDs ids) { super.ensureCapacity(size() + ids.size()); boolean changed = false; - for(DBID id : ids) { + for(DBIDIter id = ids.iter(); id.valid(); id.advance()) { changed |= add(id); } return changed; @@ -89,15 +91,20 @@ public class GenericArrayModifiableDBIDs extends ArrayList<DBID> implements Arra @Override public boolean removeDBIDs(DBIDs ids) { boolean changed = false; - for(DBID id : ids) { + for(DBIDIter id = ids.iter(); id.valid(); id.advance()) { changed |= super.remove(id); } return changed; } @Override - public boolean remove(DBID id) { - return super.remove(id); + public boolean add(DBIDRef id) { + return add(id.getDBID()); + } + + @Override + public boolean remove(DBIDRef id) { + return super.remove(id.getDBID()); } @Override @@ -111,17 +118,22 @@ public class GenericArrayModifiableDBIDs extends ArrayList<DBID> implements Arra } @Override - public DBIDIter iter() { + public DBIDMIter iter() { return new DBIDIterAdapter(iterator()); } @Override - public int binarySearch(DBID key) { - return Collections.binarySearch(this, key); + public int binarySearch(DBIDRef key) { + return Collections.binarySearch(this, key.getDBID()); } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return super.contains(o); } + + @Override + public void swap(int a, int b) { + set(a, set(b, get(a))); + } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericHashSetModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericHashSetModifiableDBIDs.java index 31a8602c..6eadf0b1 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericHashSetModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/GenericHashSetModifiableDBIDs.java @@ -24,10 +24,11 @@ package de.lmu.ifi.dbs.elki.database.ids.generic; */ import java.util.HashSet; -import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDMIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.database.ids.HashSetModifiableDBIDs; @@ -72,7 +73,7 @@ public class GenericHashSetModifiableDBIDs extends HashSet<DBID> implements Hash */ public GenericHashSetModifiableDBIDs(DBIDs c) { super(c.size()); - for(DBID id : c) { + for(DBIDIter id = c.iter(); id.valid(); id.advance()) { add(id); } } @@ -80,7 +81,7 @@ public class GenericHashSetModifiableDBIDs extends HashSet<DBID> implements Hash @Override public boolean addDBIDs(DBIDs ids) { boolean changed = false; - for(DBID id : ids) { + for(DBIDIter id = ids.iter(); id.valid(); id.advance()) { changed |= add(id); } return changed; @@ -89,23 +90,27 @@ public class GenericHashSetModifiableDBIDs extends HashSet<DBID> implements Hash @Override public boolean removeDBIDs(DBIDs ids) { boolean changed = false; - for(DBID id : ids) { + for(DBIDIter id = ids.iter(); id.valid(); id.advance()) { changed |= super.remove(id); } return changed; } @Override - public boolean remove(DBID id) { - return super.remove(id); + public boolean add(DBIDRef id) { + return super.add(id.getDBID()); + } + + @Override + public boolean remove(DBIDRef id) { + return super.remove(id.getDBID()); } @Override public boolean retainAll(DBIDs ids) { boolean modified = false; - Iterator<DBID> it = iterator(); - while(it.hasNext()) { - if(!ids.contains(it.next())) { + for(DBIDMIter it = iter(); it.valid(); it.advance()) { + if(!ids.contains(it)) { it.remove(); modified = true; } @@ -114,12 +119,12 @@ public class GenericHashSetModifiableDBIDs extends HashSet<DBID> implements Hash } @Override - public DBIDIter iter() { + public DBIDMIter iter() { return new DBIDIterAdapter(iterator()); } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return super.contains(o); } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/MaskedDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/MaskedDBIDs.java index 67c84290..13a6cc21 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/MaskedDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/MaskedDBIDs.java @@ -29,6 +29,7 @@ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.ArrayDBIDs; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; /** @@ -36,7 +37,7 @@ import de.lmu.ifi.dbs.elki.database.ids.DBIDs; * * @author Erich Schubert * - * @apiviz.uses de.lmu.ifi.dbs.elki.database.ids.DBIDs + * @apiviz.uses DBIDs */ public class MaskedDBIDs implements DBIDs { /** @@ -99,10 +100,10 @@ public class MaskedDBIDs implements DBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { // TODO: optimize. for(DBID id : this) { - if(id.equals(o)) { + if(id.sameDBID(o)) { return true; } } @@ -191,6 +192,18 @@ public class MaskedDBIDs implements DBIDs { public DBID getDBID() { return data.get(pos); } + + @Override + public boolean sameDBID(DBIDRef other) { + return getIntegerID() == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + final int thisVal = getIntegerID(); + final int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } } /** @@ -253,7 +266,7 @@ public class MaskedDBIDs implements DBIDs { @Override public boolean valid() { - return pos >= 0; + return (pos >= 0) && (pos < data.size()); } @Override @@ -270,5 +283,17 @@ public class MaskedDBIDs implements DBIDs { public DBID getDBID() { return data.get(pos); } + + @Override + public boolean sameDBID(DBIDRef other) { + return getIntegerID() == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + final int thisVal = getIntegerID(); + final int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } } -} +}
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/MergedDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/MergedDBIDs.java index 97743867..16d83a56 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/MergedDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/MergedDBIDs.java @@ -27,6 +27,7 @@ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.utilities.exceptions.AbortException; @@ -79,7 +80,7 @@ public class MergedDBIDs implements DBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { for(DBIDs child : childs) { if(child.contains(o)) { return true; diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableArrayDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableArrayDBIDs.java new file mode 100644 index 00000000..35b092c2 --- /dev/null +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableArrayDBIDs.java @@ -0,0 +1,101 @@ +package de.lmu.ifi.dbs.elki.database.ids.generic; + +/* + This file is part of ELKI: + Environment for Developing KDD-Applications Supported by Index-Structures + + Copyright (C) 2012 + Ludwig-Maximilians-Universität München + Lehr- und Forschungseinheit für Datenbanksysteme + ELKI Development Team + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU Affero General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Affero General Public License for more details. + + You should have received a copy of the GNU Affero General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +import java.util.Iterator; + +import de.lmu.ifi.dbs.elki.database.ids.ArrayDBIDs; +import de.lmu.ifi.dbs.elki.database.ids.ArrayStaticDBIDs; +import de.lmu.ifi.dbs.elki.database.ids.DBID; +import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; +import de.lmu.ifi.dbs.elki.utilities.iterator.UnmodifiableIterator; + +/** + * Unmodifiable wrapper for DBIDs. + * + * @author Erich Schubert + * + * @apiviz.uses de.lmu.ifi.dbs.elki.database.ids.DBIDs + */ +public class UnmodifiableArrayDBIDs implements ArrayStaticDBIDs { + /** + * The DBIDs we wrap. + */ + final private ArrayDBIDs inner; + + /** + * Constructor. + * + * @param inner Inner DBID collection. + */ + public UnmodifiableArrayDBIDs(ArrayDBIDs inner) { + super(); + this.inner = inner; + } + + @Override + public boolean contains(DBIDRef o) { + return inner.contains(o); + } + + @Override + public boolean isEmpty() { + return inner.isEmpty(); + } + + @SuppressWarnings("deprecation") + @Override + public Iterator<DBID> iterator() { + return new UnmodifiableIterator<DBID>(inner.iterator()); + } + + @Override + public DBIDIter iter() { + return inner.iter(); + } + + @Override + public int size() { + return inner.size(); + } + + /** + * Returns a string representation of the inner DBID collection. + */ + @Override + public String toString() { + return inner.toString(); + } + + @Override + public DBID get(int i) { + return inner.get(i); + } + + @Override + public int binarySearch(DBIDRef key) { + return inner.binarySearch(key); + } +}
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableDBIDs.java index bd68e2fb..682b2e4b 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/generic/UnmodifiableDBIDs.java @@ -27,6 +27,7 @@ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.database.ids.StaticDBIDs; import de.lmu.ifi.dbs.elki.utilities.iterator.UnmodifiableIterator; @@ -55,7 +56,7 @@ public class UnmodifiableDBIDs implements StaticDBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return inner.contains(o); } @@ -64,6 +65,7 @@ public class UnmodifiableDBIDs implements StaticDBIDs { return inner.isEmpty(); } + @SuppressWarnings("deprecation") @Override public Iterator<DBID> iterator() { return new UnmodifiableIterator<DBID>(inner.iterator()); diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerArrayStaticDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerArrayStaticDBIDs.java index ef4aee94..90ab5a6a 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerArrayStaticDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerArrayStaticDBIDs.java @@ -31,6 +31,8 @@ import de.lmu.ifi.dbs.elki.database.ids.ArrayStaticDBIDs; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDFactory; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; +import de.lmu.ifi.dbs.elki.logging.LoggingUtil; /** * Static (no modifications allowed) set of Database Object IDs. @@ -123,6 +125,24 @@ public class IntegerArrayStaticDBIDs extends AbstractList<DBID> implements Array return new IntegerDBID(ids[pos]); } + @Override + public boolean sameDBID(DBIDRef other) { + return ids[pos] == other.getIntegerID(); + } + + @Override + public boolean equals(Object other) { + if (other instanceof DBID) { + LoggingUtil.warning("Programming error detected: DBIDItr.equals(DBID). Use sameDBID()!", new Throwable()); + } + return super.equals(other); + } + + @Override + public int compareDBID(DBIDRef o) { + int anotherVal = o.getIntegerID(); + return (ids[pos] < anotherVal ? -1 : (ids[pos] == anotherVal ? 0 : 1)); + } } @Override @@ -131,7 +151,7 @@ public class IntegerArrayStaticDBIDs extends AbstractList<DBID> implements Array } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { final int oid = o.getIntegerID(); for(int i = 0; i < ids.length; i++) { if(ids[i] == oid) { @@ -164,7 +184,7 @@ public class IntegerArrayStaticDBIDs extends AbstractList<DBID> implements Array } @Override - public int binarySearch(DBID key) { + public int binarySearch(DBIDRef key) { return Arrays.binarySearch(ids, key.getIntegerID()); } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBID.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBID.java index f9e83294..66c1f980 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBID.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBID.java @@ -28,6 +28,8 @@ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; +import de.lmu.ifi.dbs.elki.logging.LoggingUtil; import de.lmu.ifi.dbs.elki.persistent.ByteArrayUtil; import de.lmu.ifi.dbs.elki.persistent.ByteBufferSerializer; import de.lmu.ifi.dbs.elki.persistent.FixedSizeByteBufferSerializer; @@ -49,7 +51,7 @@ import de.lmu.ifi.dbs.elki.persistent.FixedSizeByteBufferSerializer; * @apiviz.composedOf DynamicSerializer * @apiviz.composedOf StaticSerializer */ -class IntegerDBID implements DBID { +final class IntegerDBID implements DBID { /** * The actual object ID. */ @@ -75,6 +77,11 @@ class IntegerDBID implements DBID { this.id = id; } + @Override + public DBID getDBID() { + return this; + } + /** * Return the integer value of the object ID. * @@ -98,14 +105,29 @@ class IntegerDBID implements DBID { @Override public boolean equals(Object obj) { if(!(obj instanceof IntegerDBID)) { + if (obj instanceof DBIDRef) { + LoggingUtil.warning("Programming error: DBID.equals(DBIDRef) is not well-defined. use sameDBID!", new Throwable()); + } return false; } IntegerDBID other = (IntegerDBID) obj; return this.id == other.id; } + + @Override + public boolean sameDBID(DBIDRef other) { + return this.id == other.getIntegerID(); + } @Override - public int compareTo(DBID o) { + public int compareTo(DBIDRef o) { + int thisVal = this.id; + int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } + + @Override + public int compareDBID(DBIDRef o) { int thisVal = this.id; int anotherVal = o.getIntegerID(); return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); @@ -130,7 +152,7 @@ class IntegerDBID implements DBID { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return o.getIntegerID() == id; } @@ -140,8 +162,8 @@ class IntegerDBID implements DBID { } @Override - public int binarySearch(DBID key) { - return equals(key) ? 0 : -1; + public int binarySearch(DBIDRef key) { + return (id == key.getIntegerID()) ? 0 : -1; } /** @@ -207,6 +229,25 @@ class IntegerDBID implements DBID { public boolean valid() { return first; } + + @Override + public boolean equals(Object other) { + if (other instanceof DBID) { + LoggingUtil.warning("Programming error detected: DBIDItr.equals(DBID). Use sameDBID()!", new Throwable()); + } + return super.equals(other); + } + + @Override + public boolean sameDBID(DBIDRef other) { + return id == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + int anotherVal = o.getIntegerID(); + return (id < anotherVal ? -1 : (id == anotherVal ? 0 : 1)); + } } @Override diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBIDRange.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBIDRange.java index debe39a4..cad771d9 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBIDRange.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/IntegerDBIDRange.java @@ -30,6 +30,7 @@ import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDFactory; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; import de.lmu.ifi.dbs.elki.database.ids.DBIDRange; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; /** * Representing a DBID range allocation @@ -134,10 +135,25 @@ class IntegerDBIDRange extends AbstractList<DBID> implements DBIDRange { return new IntegerDBID(start + pos); } + @Override + public boolean equals(Object other) { + throw new UnsupportedOperationException(); + } + + @Override + public boolean sameDBID(DBIDRef other) { + return start + pos == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + int anotherVal = o.getIntegerID(); + return (start + pos < anotherVal ? -1 : (start + pos == anotherVal ? 0 : 1)); + } } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { int oid = o.getIntegerID(); if(oid < start) { return false; @@ -180,12 +196,12 @@ class IntegerDBIDRange extends AbstractList<DBID> implements DBIDRange { * @return array offset */ @Override - public int getOffset(DBID dbid) { + public int getOffset(DBIDRef dbid) { return dbid.getIntegerID() - start; } @Override - public int binarySearch(DBID key) { + public int binarySearch(DBIDRef key) { int keyid = key.getIntegerID(); if(keyid < start) { return -1; diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/SimpleDBIDFactory.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/SimpleDBIDFactory.java index 59fa34b5..8003e4ae 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/SimpleDBIDFactory.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/SimpleDBIDFactory.java @@ -28,6 +28,7 @@ import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDFactory; import de.lmu.ifi.dbs.elki.database.ids.DBIDPair; import de.lmu.ifi.dbs.elki.database.ids.DBIDRange; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.database.ids.HashSetModifiableDBIDs; import de.lmu.ifi.dbs.elki.persistent.ByteBufferSerializer; @@ -132,7 +133,7 @@ public class SimpleDBIDFactory implements DBIDFactory { } @Override - public DBIDPair makePair(DBID first, DBID second) { + public DBIDPair makePair(DBIDRef first, DBIDRef second) { return new IntegerDBIDPair(first.getIntegerID(), second.getIntegerID()); } diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TrivialDBIDFactory.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TrivialDBIDFactory.java index b38286fe..80f65f29 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TrivialDBIDFactory.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TrivialDBIDFactory.java @@ -30,6 +30,7 @@ import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDFactory; import de.lmu.ifi.dbs.elki.database.ids.DBIDPair; import de.lmu.ifi.dbs.elki.database.ids.DBIDRange; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.database.ids.HashSetModifiableDBIDs; import de.lmu.ifi.dbs.elki.persistent.ByteBufferSerializer; @@ -130,7 +131,7 @@ public class TrivialDBIDFactory implements DBIDFactory { } @Override - public DBIDPair makePair(DBID first, DBID second) { + public DBIDPair makePair(DBIDRef first, DBIDRef second) { return new IntegerDBIDPair(first.getIntegerID(), second.getIntegerID()); } diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayDBIDs.java index a060c6b8..e2bfbcd5 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayDBIDs.java @@ -29,7 +29,9 @@ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.ArrayDBIDs; import de.lmu.ifi.dbs.elki.database.ids.DBID; -import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDMIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; +import de.lmu.ifi.dbs.elki.logging.LoggingUtil; /** * Abstract base class for GNU Trove array based lists. @@ -53,7 +55,7 @@ public abstract class TroveArrayDBIDs implements ArrayDBIDs { } @Override - public DBIDIter iter() { + public DBIDMIter iter() { return new DBIDItr(getStore()); } @@ -73,12 +75,12 @@ public abstract class TroveArrayDBIDs implements ArrayDBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return getStore().contains(o.getIntegerID()); } @Override - public int binarySearch(DBID key) { + public int binarySearch(DBIDRef key) { return getStore().binarySearch(key.getIntegerID()); } @@ -89,7 +91,7 @@ public abstract class TroveArrayDBIDs implements ArrayDBIDs { * * @apiviz.exclude */ - protected static class DBIDItr implements DBIDIter { + protected static class DBIDItr implements DBIDMIter { /** * Current position */ @@ -129,5 +131,31 @@ public abstract class TroveArrayDBIDs implements ArrayDBIDs { public DBID getDBID() { return new IntegerDBID(store.get(pos)); } + + @Override + public void remove() { + store.removeAt(pos); + pos--; + } + + @Override + public boolean sameDBID(DBIDRef other) { + return store.get(pos) == other.getIntegerID(); + } + + @Override + public boolean equals(Object other) { + if (other instanceof DBID) { + LoggingUtil.warning("Programming error detected: DBIDItr.equals(DBID). Use sameDBID()!", new Throwable()); + } + return super.equals(other); + } + + @Override + public int compareDBID(DBIDRef o) { + final int thisVal = store.get(pos); + final int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayModifiableDBIDs.java index abcbba14..379ea8a6 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveArrayModifiableDBIDs.java @@ -31,6 +31,7 @@ import java.util.Comparator; import de.lmu.ifi.dbs.elki.database.ids.ArrayModifiableDBIDs; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; /** @@ -96,12 +97,12 @@ class TroveArrayModifiableDBIDs extends TroveArrayDBIDs implements ArrayModifiab } @Override - public boolean add(DBID e) { + public boolean add(DBIDRef e) { return store.add(e.getIntegerID()); } @Override - public boolean remove(DBID o) { + public boolean remove(DBIDRef o) { return store.remove(o.getIntegerID()); } @@ -141,4 +142,9 @@ class TroveArrayModifiableDBIDs extends TroveArrayDBIDs implements ArrayModifiab store.set(i, data[i].getIntegerID()); } } + + @Override + public void swap(int a, int b) { + store.set(a, store.set(b, store.get(a))); + } }
\ No newline at end of file diff --git a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveHashSetModifiableDBIDs.java b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveHashSetModifiableDBIDs.java index 11fe669c..12656f7b 100644 --- a/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveHashSetModifiableDBIDs.java +++ b/src/de/lmu/ifi/dbs/elki/database/ids/integer/TroveHashSetModifiableDBIDs.java @@ -7,6 +7,8 @@ import gnu.trove.impl.hash.TIntHash; import gnu.trove.set.hash.TIntHashSet; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.DBIDIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDMIter; +import de.lmu.ifi.dbs.elki.database.ids.DBIDRef; import de.lmu.ifi.dbs.elki.database.ids.DBIDs; import de.lmu.ifi.dbs.elki.database.ids.HashSetModifiableDBIDs; @@ -76,7 +78,7 @@ class TroveHashSetModifiableDBIDs implements HashSetModifiableDBIDs { } @Override - public DBIDIter iter() { + public DBIDMIter iter() { return new DBIDItr(store); } @@ -99,12 +101,12 @@ class TroveHashSetModifiableDBIDs implements HashSetModifiableDBIDs { } @Override - public boolean add(DBID e) { + public boolean add(DBIDRef e) { return store.add(e.getIntegerID()); } @Override - public boolean remove(DBID o) { + public boolean remove(DBIDRef o) { return store.remove(o.getIntegerID()); } @@ -142,7 +144,7 @@ class TroveHashSetModifiableDBIDs implements HashSetModifiableDBIDs { } @Override - public boolean contains(DBID o) { + public boolean contains(DBIDRef o) { return store.contains(o.getIntegerID()); } @@ -153,7 +155,7 @@ class TroveHashSetModifiableDBIDs implements HashSetModifiableDBIDs { * * @apiviz.exclude */ - protected static class DBIDItr extends THashPrimitiveIterator implements DBIDIter { + protected static class DBIDItr extends THashPrimitiveIterator implements DBIDMIter { /** * The has we access */ @@ -189,5 +191,17 @@ class TroveHashSetModifiableDBIDs implements HashSetModifiableDBIDs { public DBID getDBID() { return new IntegerDBID(hash._set[_index]); } + + @Override + public boolean sameDBID(DBIDRef other) { + return getIntegerID() == other.getIntegerID(); + } + + @Override + public int compareDBID(DBIDRef o) { + final int thisVal = hash._set[_index]; + final int anotherVal = o.getIntegerID(); + return (thisVal < anotherVal ? -1 : (thisVal == anotherVal ? 0 : 1)); + } } }
\ No newline at end of file |