package de.lmu.ifi.dbs.elki.distance.similarityfunction; /* This file is part of ELKI: Environment for Developing KDD-Applications Supported by Index-Structures Copyright (C) 2011 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 . */ import java.util.Iterator; import de.lmu.ifi.dbs.elki.database.ids.DBID; import de.lmu.ifi.dbs.elki.database.ids.SetDBIDs; import de.lmu.ifi.dbs.elki.database.relation.Relation; import de.lmu.ifi.dbs.elki.distance.distancevalue.Distance; import de.lmu.ifi.dbs.elki.distance.distancevalue.IntegerDistance; import de.lmu.ifi.dbs.elki.index.preprocessed.snn.SharedNearestNeighborIndex; import de.lmu.ifi.dbs.elki.index.preprocessed.snn.SharedNearestNeighborPreprocessor; import de.lmu.ifi.dbs.elki.utilities.optionhandling.parameterization.Parameterization; /** * SharedNearestNeighborSimilarityFunction with a pattern defined to accept * Strings that define a non-negative Integer. * * @author Arthur Zimek * * @apiviz.has de.lmu.ifi.dbs.elki.index.preprocessed.snn.SharedNearestNeighborIndex.Factory * @apiviz.uses Instance oneway - - «create» * * @param object type * @param distance type */ // todo arthur comment class public class SharedNearestNeighborSimilarityFunction> extends AbstractIndexBasedSimilarityFunction, SetDBIDs, IntegerDistance> { /** * Constructor. * * @param indexFactory Index factory. */ public SharedNearestNeighborSimilarityFunction(SharedNearestNeighborIndex.Factory> indexFactory) { super(indexFactory); } @Override public IntegerDistance getDistanceFactory() { return IntegerDistance.FACTORY; } static protected int countSharedNeighbors(SetDBIDs neighbors1, SetDBIDs neighbors2) { int intersection = 0; Iterator iter1 = neighbors1.iterator(); Iterator iter2 = neighbors2.iterator(); DBID neighbors1ID = null; DBID neighbors2ID = null; if(iter1.hasNext()) { neighbors1ID = iter1.next(); } if(iter2.hasNext()) { neighbors2ID = iter2.next(); } while((iter1.hasNext() || iter2.hasNext()) && neighbors1ID != null && neighbors2ID != null) { if(neighbors1ID.equals(neighbors2ID)) { intersection++; if(iter1.hasNext()) { neighbors1ID = iter1.next(); } else { neighbors1ID = null; } if(iter2.hasNext()) { neighbors2ID = iter2.next(); } else { neighbors2ID = null; } } else if(neighbors2ID.compareTo(neighbors1ID) > 0) { if(iter1.hasNext()) { neighbors1ID = iter1.next(); } else { neighbors1ID = null; } } else // neighbors1ID > neighbors2ID { if(iter2.hasNext()) { neighbors2ID = iter2.next(); } else { neighbors2ID = null; } } } return intersection; } @SuppressWarnings("unchecked") @Override public Instance instantiate(Relation database) { SharedNearestNeighborIndex indexi = indexFactory.instantiate((Relation) database); return (Instance) new Instance((Relation) database, indexi); } /** * TODO: document * * @author Erich Schubert * * @apiviz.uses SharedNearestNeighborIndex * * @param */ public static class Instance> extends AbstractIndexBasedSimilarityFunction.Instance, SetDBIDs, IntegerDistance> { public Instance(Relation database, SharedNearestNeighborIndex preprocessor) { super(database, preprocessor); } @Override public IntegerDistance similarity(DBID id1, DBID id2) { SetDBIDs neighbors1 = index.getNearestNeighborSet(id1); SetDBIDs neighbors2 = index.getNearestNeighborSet(id2); return new IntegerDistance(countSharedNeighbors(neighbors1, neighbors2)); } @Override public IntegerDistance getDistanceFactory() { return IntegerDistance.FACTORY; } } /** * Parameterization class. * * @author Erich Schubert * * @apiviz.exclude */ public static class Parameterizer> extends AbstractIndexBasedSimilarityFunction.Parameterizer>> { @Override protected void makeOptions(Parameterization config) { super.makeOptions(config); configIndexFactory(config, SharedNearestNeighborIndex.Factory.class, SharedNearestNeighborPreprocessor.Factory.class); } @Override protected SharedNearestNeighborSimilarityFunction makeInstance() { return new SharedNearestNeighborSimilarityFunction(factory); } } }