From: <ste...@us...> - 2006-11-30 13:40:44
|
Revision: 7387 http://svn.sourceforge.net/cdk/?rev=7387&view=rev Author: steinbeck Date: 2006-11-30 05:40:43 -0800 (Thu, 30 Nov 2006) Log Message: ----------- Changed generation scheme to return generated structures in small portions to registered listeners. Modified Paths: -------------- trunk/cdk/src/org/openscience/cdk/structgen/deterministic/GENMDeterministicGenerator.java Modified: trunk/cdk/src/org/openscience/cdk/structgen/deterministic/GENMDeterministicGenerator.java =================================================================== --- trunk/cdk/src/org/openscience/cdk/structgen/deterministic/GENMDeterministicGenerator.java 2006-11-30 13:39:47 UTC (rev 7386) +++ trunk/cdk/src/org/openscience/cdk/structgen/deterministic/GENMDeterministicGenerator.java 2006-11-30 13:40:43 UTC (rev 7387) @@ -21,7 +21,6 @@ package org.openscience.cdk.structgen.deterministic; import java.io.FileWriter; -import java.io.IOException; import java.io.PrintWriter; import java.util.ArrayList; import java.util.List; @@ -31,20 +30,39 @@ import org.openscience.cdk.interfaces.IAtom; import org.openscience.cdk.interfaces.IAtomContainer; import org.openscience.cdk.interfaces.IMolecule; +import org.openscience.cdk.structgen.StructureGenerationListener; import org.openscience.cdk.tools.LoggingTool; import org.openscience.cdk.tools.MFAnalyser; + + /** - * An adapted implementation of Molodtsov structure generator. - * The final part is not the original idea, such as - * normalization, also the author omitted the strong canonicity as it needs other algorithms. - * Therefore, it is a mixture - * of Molodtsov structure generator with other ideas. + * An adapted implementation of the Molodtsov structure generator. + * Changes to the original idea include issues of + * normalization and strong canonicity criteria + * + * <pre> + * gdg = new GENMDeterministicGenerator(formula,""); + * gdg.addListener(this); + * gdg.setStructuresAtATime(500); + * gdg.generate(); + * </pre> + * + * Please note that the number of isomers generated by this generator can quickly + * become quite large and their storage in memory will take some space. + * In order to handle to large amount of potential data, the generator hands you the + * structures in small packets. You register with the generator as a + * StructureGeneratorListener. In the respective stateChanged() method which you + * must implement, you can do with the latest list of generated structures + * whatever you want. Please not that the generatore deletes things internally + * after handing over the list. Make sure to remove reference to structure in + * which you are not interested anymore, to the garbage collector can clean them up. * * <p>Details are found in the following papers * {@cdk.cite Molodtsov94, Molchanova96, Hu94, Hu94b, Hu99}. * * @author Junfeng Hao + * @author Christoph Steinbeck * @cdk.created 2004-02-16 */ public class GENMDeterministicGenerator { @@ -52,7 +70,7 @@ private LoggingTool logger; private int numberOfSetFragment; - private int numberOfStructure; + private int numberOfStructures; private IAtomContainer atomContainer; private int[] molecularFormula; private int[] numberOfBasicUnit; @@ -60,12 +78,18 @@ private List basicFragment; private List structures; private PrintWriter structureout; - + private long returnedStructureCount = 500; private static double LOST=0.000000000001; + private List listeners = null; + boolean hasMoreStructures = false; + int structuresAtATime = 500; + /** - * Constructor for the GENMDeterministicGenerator object. This constructor is only - * for molecular formula. + * Constructor for the GENMDeterministicGenerator. + * Allows for setting the molecular formula for which the + * isomers are to be generated as well as for setting an output path + * for a file with generated structures. * * @param mf molecular formula string * @param path Path to the file used for writing structures. Leave blank if current directory should be used. @@ -75,7 +99,7 @@ logger = new LoggingTool(GENMDeterministicGenerator.class); numberOfSetFragment=0; - numberOfStructure=0; + numberOfStructures=0; logger.debug(mf); MFAnalyser mfa = new MFAnalyser(mf, new AtomContainer()); molecularFormula=new int[12]; @@ -83,46 +107,34 @@ numberOfBasicFragment=new int[34]; basicFragment=new ArrayList(); structures=new ArrayList(); - - + listeners = new ArrayList(); structureout=new PrintWriter(new FileWriter(path+"structuredata.txt"),true); - initializeParameters(); analyseMolecularFormula(mfa); - generateBasicUnits(); - logger.debug("numberofstructure is="+numberOfStructure); + } - /** - * Constructor for GENMDeterministicGenerator object. This constructor could be - * used for a set of basic units. + * Central method of this Generator. Call * - * @param basicUnits Vector contain a basic unit set - * @param path Path to the file used for writing structures. Leave blank if current directory should be used. + * @throws Exception */ - public GENMDeterministicGenerator(List basicUnits, String path) throws IOException,Exception + public void generate() throws Exception { - numberOfSetFragment=0; - numberOfStructure=0; - numberOfBasicUnit=new int[23]; - numberOfBasicFragment=new int[34]; - basicFragment=new ArrayList(); - structures=new ArrayList(); + generateBasicUnits(); + logger.debug("numberofstructure is="+numberOfStructures); + fireChange(); - logger = new org.openscience.cdk.tools.LoggingTool(this); - - structureout=new PrintWriter(new FileWriter(path+"structuredata.txt"),true); - - initializeParameters(); + } + + + public void setBasicUnits(List basicUnits) + { if(basicUnits!=null)getBasicUnit(basicUnits); else logger.error("input false"); - generateBasicFragments(); - //System.out.println("numberofstructure is="+numberOfStructure); } - /** * Get basic units from input information. * @@ -2171,25 +2183,25 @@ for(j=1;j<=b[0];j++) storedSymbolOfStructure[k1+j-1]=b[j]; totalNumberOfThisSet[0]+=1; - numberOfStructure+=1; + numberOfStructures+=1; if(decomposedNumber>0) { - writeToFile(originalSet,numberOfStructure, originMatrix); - if(numberOfStructure<500) - convertToMol(originalSet,originMatrix,structures); + //writeToFile(originalSet,numberOfStructures, originMatrix); + convertToMol(originalSet,originMatrix,structures); // convertToSMILES(originalSet,originMatrix,smiles); - // writeToFile(setOfBasicFragment,numberOfStructure, adjacencyMatrix); + // writeToFile(setOfBasicFragment,numberOfStructures, adjacencyMatrix); } else { - writeToFile(setOfBasicFragment,numberOfStructure, adjacencyMatrix); - if(numberOfStructure<500) - convertToMol(setOfBasicFragment,adjacencyMatrix,structures); + //writeToFile(setOfBasicFragment,numberOfStructures, adjacencyMatrix); + convertToMol(setOfBasicFragment,adjacencyMatrix,structures); // convertToSMILES(setOfBasicFragment,adjacencyMatrix,smiles); } + if (structures.size() >= structuresAtATime) fireChange(); } + /** * Canonicalize the structure based on All-Path algorithm. * @@ -2747,11 +2759,64 @@ * * @return the number of isomers */ - public int getNumberOfStructure() + public int getNumberOfStructures() { - return this.numberOfStructure; + return this.numberOfStructures; } + + /* + * Listener notification support methods START here + */ + /** + * Adds a listener to the EventListener list + * + * @param x The eventlistener to add + */ + public void addListener(StructureGenerationListener x) + { + if (listeners == null) listeners = new ArrayList(); + listeners.add(x); + } + + + /** + * Description of the Method + * + * @param x Description of Parameter + */ + public void removeChangeListener(StructureGenerationListener x) + { + listeners.remove(x); + } + + + /** + * Description of the Method + */ + protected void fireChange() + { + for (int i = 0; i < listeners.size(); i++) + { + List list = new ArrayList(); + for (int f = 0; f < structures.size(); f++) + { + list.add(structures.get(f)); + } + + StructureGenerationListener cl = (StructureGenerationListener) listeners.get(i); + + try { + cl.stateChanged(list); + } catch (Exception e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + structures.clear(); + } + + /** * As only used in this class might now, define it as an inner class. * It just works as fragment class. @@ -2821,6 +2886,29 @@ public void setAtomContainer(IAtomContainer atomContainer) { this.atomContainer = atomContainer; } + + + public long getReturnedStructureCount() { + return returnedStructureCount; + } + + + public void setReturnedStructureCount(long returnedStructureCount) { + this.returnedStructureCount = returnedStructureCount; + } + + public boolean hasMoreStructures() { + return hasMoreStructures; + } + + public int getStructuresAtATime() { + return structuresAtATime; + } + + public void setStructuresAtATime(int structuresAtATime) { + this.structuresAtATime = structuresAtATime; + } + } This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |