Author: scooter
Date: 2013-02-19 10:44:38 -0800 (Tue, 19 Feb 2013)
New Revision: 31126

Added:
   csplugins/trunk/ucsf/scooter/chemViz/lib/cdk-1.5.1.git.jar
   csplugins/trunk/ucsf/scooter/chemViz/lib/commons-math3-3.0.jar
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/Fragment.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/JobType.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSS.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSSThread.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/TaskUpdater.java
Removed:
   csplugins/trunk/ucsf/scooter/chemViz/lib/cdk-1.4.15-1.jar
Modified:
   csplugins/trunk/ucsf/scooter/chemViz/build.xml
   csplugins/trunk/ucsf/scooter/chemViz/resources/plugin.props
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/model/Compound.java
   
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/similarity/CDKTanimotoScore.java
   
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/AbstractCompoundTask.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/CreateMCSSTask.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/SMARTSSearchTask.java
   csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/ui/CompoundTable.java
Log:
Reimplementation of MCSS with help from Asad.


Modified: csplugins/trunk/ucsf/scooter/chemViz/build.xml
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/build.xml      2013-02-15 22:35:56 UTC 
(rev 31125)
+++ csplugins/trunk/ucsf/scooter/chemViz/build.xml      2013-02-19 18:44:38 UTC 
(rev 31126)
@@ -103,8 +103,8 @@
   =====================================================================
   -->
   <target name="jar" depends="compile" description="makes a jar for Cytoscape 
under development">
-    <mkdir dir="${build.dir}/classes/lib"/>
-    <unzip dest="${build.dir}/classes/lib/">
+    <mkdir dir="${build.dir}/lib"/>
+    <unzip dest="${build.dir}/lib/">
       <fileset dir="${lib.dir}">
         <include name="*.jar"/>
       </fileset>
@@ -118,7 +118,7 @@
         <attribute name="Cytoscape-Plugin" value="chemViz.ChemViz" />
       </manifest>
       <fileset dir="${build.dir}/classes" />
-      <fileset dir="${build.dir}/classes/lib"/>
+      <fileset dir="${build.dir}/lib" />
     </jar>
   </target>
 

Deleted: csplugins/trunk/ucsf/scooter/chemViz/lib/cdk-1.4.15-1.jar
===================================================================
(Binary files differ)

Added: csplugins/trunk/ucsf/scooter/chemViz/lib/cdk-1.5.1.git.jar
===================================================================
(Binary files differ)


Property changes on: csplugins/trunk/ucsf/scooter/chemViz/lib/cdk-1.5.1.git.jar
___________________________________________________________________
Added: svn:mime-type
   + application/zip

Added: csplugins/trunk/ucsf/scooter/chemViz/lib/commons-math3-3.0.jar
===================================================================
(Binary files differ)


Property changes on: 
csplugins/trunk/ucsf/scooter/chemViz/lib/commons-math3-3.0.jar
___________________________________________________________________
Added: svn:mime-type
   + application/zip

Modified: csplugins/trunk/ucsf/scooter/chemViz/resources/plugin.props
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/resources/plugin.props 2013-02-15 
22:35:56 UTC (rev 31125)
+++ csplugins/trunk/ucsf/scooter/chemViz/resources/plugin.props 2013-02-19 
18:44:38 UTC (rev 31126)
@@ -31,4 +31,4 @@
 pluginAuthorsIntsitutions=John "Scooter" Morris:UCSF;Dazhi Jiao:Indiana 
University School of Informatics
 
 # Date this plugin/plugin version was released
-releaseDate=December 1th, 2012
+releaseDate=March 1st, 2013

Modified: csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/model/Compound.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/model/Compound.java        
2013-02-15 22:35:56 UTC (rev 31125)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/model/Compound.java        
2013-02-19 18:44:38 UTC (rev 31126)
@@ -73,10 +73,9 @@
 import cytoscape.util.URLUtil;
 import giny.view.NodeView;
 
+import org.openscience.cdk.AtomContainer;
 import org.openscience.cdk.CDKConstants;
 import org.openscience.cdk.ChemModel;
-import org.openscience.cdk.Molecule;
-import org.openscience.cdk.MoleculeSet;
 import org.openscience.cdk.aromaticity.CDKHueckelAromaticityDetector;
 import org.openscience.cdk.atomtype.CDKAtomTypeMatcher;
 import org.openscience.cdk.config.IsotopeFactory;
@@ -91,13 +90,12 @@
 import org.openscience.cdk.inchi.InChIToStructure;
 import org.openscience.cdk.interfaces.IAtom;
 import org.openscience.cdk.interfaces.IAtomContainer;
+import org.openscience.cdk.interfaces.IAtomContainerSet;
 import org.openscience.cdk.interfaces.IAtomType;
 import org.openscience.cdk.interfaces.IAtomType.Hybridization;
 import org.openscience.cdk.interfaces.IChemModel;
 import org.openscience.cdk.interfaces.IIsotope;
 import org.openscience.cdk.interfaces.IMolecularFormula;
-import org.openscience.cdk.interfaces.IMolecule;
-import org.openscience.cdk.interfaces.IMoleculeSet;
 import org.openscience.cdk.interfaces.IRing;
 import org.openscience.cdk.interfaces.IRingSet;
 import org.openscience.cdk.layout.StructureDiagramGenerator;
@@ -135,7 +133,7 @@
  * could have multiple Compounds, either by having multiple attributes that 
contain compound descriptors or
  * by having a single attribute that contains multiple descriptors (e.g. 
comma-separated SMILES strings).  The
  * creation of a Compound results in the building of a cached 2D image for 
that compound, as well as the creation
- * of the CDK IMolecule, which is used for conversion from InChI to SMILES, 
for calculation of the molecular weight,
+ * of the CDK IAtomContainer, which is used for conversion from InChI to 
SMILES, for calculation of the molecular weight,
  * and for the calculation of Tanimoto coefficients.
  */
 
@@ -309,8 +307,8 @@
        protected Image renderedImage;
        protected boolean laidOut;
        private AttriType attrType;
-       private IMolecule iMolecule;
-       private IMolecule iMolecule3D;
+       private IAtomContainer iMolecule;
+       private IAtomContainer iMolecule3D;
        private BitSet fingerPrint;
        private IFingerprinter fp;
        private int lastImageWidth = -1;
@@ -336,7 +334,7 @@
        }
 
        /**
-        * This alternative form of the constructor is called when we've 
calculated an IMolecule internally and it
+        * This alternative form of the constructor is called when we've 
calculated an IAtomContainer internally and it
         * bypasses the creation.
         *
         * @param source the graph object that holds this compound
@@ -344,7 +342,7 @@
         * @param mstring the compound descriptor itself
         * @param attrType the type of the compound descriptor (inchi or smiles)
         */
-       public Compound(GraphObject source, String attribute, String mstring, 
IMolecule molecule,
+       public Compound(GraphObject source, String attribute, String mstring, 
IAtomContainer molecule,
                        AttriType attrType) {
                this.source = source;
                this.attribute = attribute;
@@ -369,7 +367,7 @@
        }
 
 
-       public void createStructure(IMolecule molecule) {
+       public void createStructure(IAtomContainer molecule) {
                long startTime = Calendar.getInstance().getTimeInMillis();
 
                this.renderedImage = null;
@@ -412,7 +410,7 @@
                long smilesTime = Calendar.getInstance().getTimeInMillis();
                totalSMILESTime += smilesTime-fpTime;
 
-               // At this point, we should have an IMolecule
+               // At this point, we should have an IAtomContainer
                try { 
                        
CDKHueckelAromaticityDetector.detectAromaticity(iMolecule);
 
@@ -470,11 +468,11 @@
        }
 
        /**
-        * Return the CDK IMolecule for this compound
+        * Return the CDK IAtomContainer for this compound
         *
-        * @return the IMolecule for this compound
+        * @return the IAtomContainer for this compound
         */
-       public IMolecule getIMolecule() {
+       public IAtomContainer getIAtomContainer() {
                return iMolecule;
        }
 
@@ -487,7 +485,7 @@
                if (fingerPrint == null) {
                        try {
                                synchronized (fp) {
-                                       fingerPrint = 
fp.getFingerprint(addh(iMolecule));
+                                       fingerPrint = 
fp.getBitFingerprint(addh(iMolecule)).asBitSet();
                                }
                        } catch (Exception e) {
                                logger.warning("Error calculating fingerprint: 
"+e);
@@ -881,11 +879,11 @@
                                // Is the structure connected?
                                if 
(!ConnectivityChecker.isConnected(iMolecule)) {
                                        // No, for now, find the largest 
component and use that exclusively
-                                       IMoleculeSet molSet = 
ConnectivityChecker.partitionIntoMolecules(iMolecule);
-                                       IMolecule largest = 
molSet.getMolecule(0);
-                                       for (int i = 0; i < 
molSet.getMoleculeCount(); i++) {
-                                               if 
(molSet.getMolecule(i).getAtomCount() > largest.getAtomCount())
-                                                       largest = 
molSet.getMolecule(i);
+                                       IAtomContainerSet molSet = 
ConnectivityChecker.partitionIntoMolecules(iMolecule);
+                                       IAtomContainer largest = 
molSet.getAtomContainer(0);
+                                       for (int i = 0; i < 
molSet.getAtomContainerCount(); i++) {
+                                               if 
(molSet.getAtomContainer(i).getAtomCount() > largest.getAtomCount())
+                                                       largest = 
molSet.getAtomContainer(i);
                                        }
                                        iMolecule = largest;
                                }
@@ -925,10 +923,10 @@
                }
        }
 
-       private IMolecule addh(IMolecule mol) {
-               IMolecule molH;
+       private IAtomContainer addh(IAtomContainer mol) {
+               IAtomContainer molH;
                try {
-                       molH = (IMolecule)mol.clone();
+                       molH = (IAtomContainer)mol.clone();
                } catch (Exception e) {
                        return mol;
                }
@@ -968,7 +966,7 @@
                                return null;
                        }
 
-                       IMolecule molecule = new 
Molecule(intostruct.getAtomContainer());
+                       IAtomContainer molecule = new 
AtomContainer(intostruct.getAtomContainer());
                        // Use the molecule to create a SMILES string
                        SmilesGenerator sg = new SmilesGenerator();
                        return sg.createSMILES(molecule);
@@ -979,7 +977,7 @@
 
        }
 
-       private Image blankImage(IMolecule mol, int width, int height) {
+       private Image blankImage(IAtomContainer mol, int width, int height) {
                final String noImage = "Image Unavailable";
 
                if (width == 0 || height == 0)

Modified: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/similarity/CDKTanimotoScore.java
===================================================================
--- 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/similarity/CDKTanimotoScore.java
   2013-02-15 22:35:56 UTC (rev 31125)
+++ 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/similarity/CDKTanimotoScore.java
   2013-02-19 18:44:38 UTC (rev 31126)
@@ -5,7 +5,6 @@
 import org.openscience.cdk.DefaultChemObjectBuilder;
 import org.openscience.cdk.exception.InvalidSmilesException;
 import org.openscience.cdk.fingerprint.Fingerprinter;
-import org.openscience.cdk.interfaces.IMolecule;
 import org.openscience.cdk.similarity.Tanimoto;
 import org.openscience.cdk.smiles.SmilesParser;
 

Modified: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/AbstractCompoundTask.java
===================================================================
--- 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/AbstractCompoundTask.java
    2013-02-15 22:35:56 UTC (rev 31125)
+++ 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/AbstractCompoundTask.java
    2013-02-19 18:44:38 UTC (rev 31126)
@@ -247,13 +247,13 @@
                return cList;
        }
 
-       protected void updateMonitor() {
+       protected synchronized void updateMonitor() {
                if (monitor == null || totalObjects == 0) return;
                
monitor.setPercentCompleted((int)(((double)objectCount/(double)totalObjects) * 
100.0));
                objectCount++;
        }
 
-       protected void setStatus(String status) {
+       protected synchronized void setStatus(String status) {
                if (monitor != null) monitor.setStatus(status);
        }
 

Modified: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/CreateMCSSTask.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/CreateMCSSTask.java  
2013-02-15 22:35:56 UTC (rev 31125)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/CreateMCSSTask.java  
2013-02-19 18:44:38 UTC (rev 31126)
@@ -46,6 +46,7 @@
 import java.util.concurrent.Executors;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Future;
+import java.util.logging.Level;
 
 import giny.model.GraphObject;
 import giny.view.EdgeView;
@@ -65,31 +66,25 @@
 import chemViz.ui.ChemInfoSettingsDialog;
 import chemViz.ui.CompoundPopup;
 
-import org.openscience.cdk.Molecule;
-import org.openscience.cdk.aromaticity.CDKHueckelAromaticityDetector;
-import org.openscience.cdk.exception.CDKException;
-import org.openscience.cdk.interfaces.IAtom;
 import org.openscience.cdk.interfaces.IAtomContainer;
-import org.openscience.cdk.interfaces.IMolecule;
-// import org.openscience.cdk.isomorphism.UniversalIsomorphismTester;
 import org.openscience.cdk.smiles.SmilesGenerator;
-import org.openscience.cdk.tools.manipulator.AtomContainerManipulator;
-import org.openscience.cdk.smsd.Isomorphism;
-import org.openscience.cdk.smsd.interfaces.Algorithm;
 
+import tools.mcss.JobType;
+import tools.mcss.MCSS;
+import tools.mcss.TaskUpdater;
 
 /**
  * The CreateCompoundsTask fetches all of the compounds defined by the
  * object passed in its constructor and provides some methods to allow
  * the caller to fetch the compounds when the task is complete.
  */
-public class CreateMCSSTask extends AbstractCompoundTask {
+public class CreateMCSSTask extends AbstractCompoundTask implements 
TaskUpdater {
        List<GraphObject> objectList;
        ChemInfoSettingsDialog dialog;
        String type;
        CyAttributes attributes;
        List<Compound> compoundList;
-       IMolecule mcss = null;
+       IAtomContainer mcss = null;
        boolean showResult = false;
        boolean createGroup = false;
        boolean calculationComplete = false;
@@ -128,11 +123,41 @@
                return g.createSMILES(mcss);
        }
 
+       public void setTotalCount(int count) {
+               totalObjects = count;
+               objectCount = 0;
+       }
+
+       public synchronized void incrementCount() {
+               updateMonitor();
+       }
+
+       public synchronized void updateStatus(String status) {
+               setStatus(status);
+       }
+
+       public synchronized void logException(String className, Level level, 
String message, Exception exception) {
+               if (message == null) message = exception.getMessage();
+
+               if (level == Level.SEVERE) {
+                       monitor.setException(exception, "Fatal error in 
"+className+": "+message);
+               }
+
+               if (level == Level.WARNING)
+                       logger.warning("Error in "+className+": "+message);
+               else if(level == Level.INFO)
+                       logger.info(className+": "+message);
+               else
+                       logger.debug(className+": "+message);
+       }
+
        /**
         * Runs the task -- this will get all of the compounds, fetching the 
images (if necessary) and creates the popup.
         */
        public void run() {
+               long startTime = Calendar.getInstance().getTimeInMillis();
                int maxThreads = dialog.getMaxThreads();
+               setStatus("Getting compounds");
                compoundList = getCompounds(objectList, attributes,
                                 
dialog.getCompoundAttributes(type,AttriType.smiles),
                                 
dialog.getCompoundAttributes(type,AttriType.inchi), maxThreads);
@@ -142,19 +167,23 @@
 
                List<IAtomContainer> mcssList = 
Collections.synchronizedList(new 
ArrayList<IAtomContainer>(compoundList.size()));
                for (Compound c: compoundList) {
-                       mcssList.add(c.getIMolecule());
+                       mcssList.add(c.getIAtomContainer());
                }
 
                int pass = 0;
                while (mcssList.size() > 1) {
-                       mcssList = calculateMCSS(mcssList, nThreads);
-                       System.out.println("calculateMCSS returns 
"+mcssList.size()+" structures");
+                       MCSS mcssJob = new MCSS(mcssList, JobType.MCS, this, 
nThreads);
+                       mcssList = mcssJob.getCalculateMCSS();
+                       // System.out.println("calculateMCSS returns 
"+mcssList.size()+" structures");
                        pass++;
                        if (canceled) break;
                }
                if (mcssList.size() == 1)
-                       mcss = (IMolecule)mcssList.get(0);
+                       mcss = (IAtomContainer)mcssList.get(0);
 
+               long endCalcTime = Calendar.getInstance().getTimeInMillis();
+               setStatus("Done. Total time: "+(endCalcTime-startTime)+"ms");
+
                calculationComplete = true;     
                if (showResult) {
                        String mcssSmiles = getMCSSSmiles();
@@ -226,155 +255,4 @@
        }
 
        public List<Compound>getCompoundList() { return compoundList; }
-
-
-       private List<IAtomContainer> 
calculateMCSS(List<IAtomContainer>mcssList, int nThreads) {
-               List<IAtomContainer> newMCSSList = 
Collections.synchronizedList(new ArrayList<IAtomContainer>(nThreads));
-               int taskNumber = 0;
-
-               if (nThreads == 1) {
-                       GetMCSSTask task = new GetMCSSTask(mcssList, 
newMCSSList, 1);
-                       task.call();
-                       return newMCSSList;
-               } else {
-                       List<Future<IAtomContainer>> futureList = new 
ArrayList<Future<IAtomContainer>>();
-                       ExecutorService threadPool = 
Executors.newFixedThreadPool(nThreads);
-                       int step = 
(int)Math.ceil((double)mcssList.size()/(double)nThreads);
-                       if (step < 2) step = 2; // Can't have a step size of 
less than 2
-                       for (int i = 0; i < mcssList.size(); i=i+step) {
-                               int endPoint = i+step;
-                               if (endPoint > mcssList.size())
-                                       endPoint = mcssList.size();
-                               List<IAtomContainer> subList = new 
ArrayList<IAtomContainer>(mcssList.subList(i, endPoint));
-                               if (subList.size() > 1)
-                                       futureList.add(threadPool.submit(new 
GetMCSSTask(subList, null, taskNumber++)));
-                               else
-                                       newMCSSList.add(subList.get(0));
-                       }
-
-                       for (Future<IAtomContainer> container: futureList) {
-                               if (container == null) continue;
-                               try {
-                                       IAtomContainer f = container.get();
-                                       if (f != null)
-                                               
newMCSSList.add(container.get());
-                               } catch (Exception e) {
-                                       logger.warning("Execution exception: 
"+e);
-                                       System.out.println("Execution 
exception: "+e);
-                                       e.printStackTrace();
-                               }
-                       }
-
-                       threadPool.shutdown();
-
-/*
-                       ExecutorService threadPool = 
Executors.newFixedThreadPool(nThreads);
-                       try {
-                               threadPool.invokeAll(taskList);
-                       } catch (Exception e) {
-                               logger.warning("Execution exception: "+e);
-                               System.out.println("Execution exception: "+e);
-                       }
-*/
-               }
-               return newMCSSList;
-       }
-
-       private class GetMCSSTask implements Callable <IAtomContainer> {
-               List<IAtomContainer> mcssList;
-               List<IAtomContainer> resultsList;
-               int taskNumber = 0;
-               IAtomContainer innerMcss = null;
-
-               public GetMCSSTask(List<IAtomContainer>mcssList, 
List<IAtomContainer>resultsList, int taskNumber) {
-                       this.mcssList = mcssList;
-                       this.resultsList = resultsList;
-                       this.taskNumber = taskNumber;
-                       mcss = null;
-               }
-
-               public synchronized IAtomContainer call() {
-                       // System.out.println("Calling MCSSTask "+taskNumber+" 
with "+mcssList.size()+" items");
-                       long startTime = 
Calendar.getInstance().getTimeInMillis();
-                       innerMcss = 
AtomContainerManipulator.removeHydrogens(mcssList.get(0));
-
-                               long calcTime = startTime;
-                               for (int index = 1; index < mcssList.size(); 
index++) {
-                                       Isomorphism comparison = new 
Isomorphism(Algorithm.DEFAULT, true);
-                                       
comparison.setBondSensitiveTimeOut(0.5); // Increase timeout to 30 seconds
-                                       IAtomContainer target = 
AtomContainerManipulator.removeHydrogens(mcssList.get(index));
-                                       try {
-                                               // System.out.println("mcss for 
task "+taskNumber+" has "+innerMcss.getAtomCount()+" atoms, and 
"+innerMcss.getBondCount()+" bonds");
-                                               // System.out.println("target 
for task "+taskNumber+" has "+target.getAtomCount()+" atoms, and 
"+target.getBondCount()+" bonds");
-                                               // 
System.out.println("comparison for task "+taskNumber+" is "+comparison);
-                                               comparison.init(innerMcss, 
target, true, true);
-                                               // 
comparison.setChemFilters(true, true, true);
-                                               innerMcss = getMCSS(comparison);
-                                       } catch (CDKException e) {
-                                               logger.warning("CDKException: 
"+e);
-                                       } catch (Exception e) {
-                                               logger.warning("Exception: "+e);
-                                       }
-
-                                       long endCalcTime = 
Calendar.getInstance().getTimeInMillis();
-                                       // System.out.println("Task 
"+taskNumber+" index "+index+" took "+(endCalcTime-calcTime)+"ms");
-                                       calcTime = endCalcTime;
-                                       if (innerMcss == null || canceled) 
break;
-                               }
-                       if (resultsList != null)
-                               resultsList.add(innerMcss);
-                       long endTime = Calendar.getInstance().getTimeInMillis();
-                       System.out.println("Done: task "+taskNumber+" took 
"+(endTime-startTime)+"ms");
-                       return innerMcss;
-               }
-
-               private synchronized IMolecule getMCSS(Isomorphism comparison) {
-                       // if (comparison.getAllAtomMapping() == null) return 
null;
-                       List<IAtomContainer> matchList = new 
ArrayList<IAtomContainer>();
-                       IAtomContainer mol1 = comparison.getReactantMolecule();
-                       // IAtomContainer mol2 = 
comparison.getProductMolecule();
-                       for (Map<IAtom,IAtom> mapping: 
comparison.getAllAtomMapping()) {
-                               IAtomContainer match = getMatchedSubgraph(mol1, 
mapping);
-                               matchList.add(match);
-                       }
-                       return maximumStructure(matchList);
-               }
-
-               private synchronized IAtomContainer 
getMatchedSubgraph(IAtomContainer container, Map<IAtom, IAtom> matches) {
-                       IAtomContainer needle = 
container.getBuilder().newInstance(IAtomContainer.class, container);
-                       // Every atom in our structure that *doesn't* have an 
entry in the matches map should be removed
-                       List<IAtom> atomListToBeRemoved = new 
ArrayList<IAtom>();
-                       for (IAtom containerAtom : container.atoms()) {
-                               if (!matches.containsKey(containerAtom)) {
-                                       int index = 
container.getAtomNumber(containerAtom);
-                                       
atomListToBeRemoved.add(needle.getAtom(index));
-                               }
-                       }
-                       for (IAtom removeAtom : atomListToBeRemoved) {
-                               
needle.removeAtomAndConnectedElectronContainers(removeAtom);
-                       }
-                       return needle;
-    }
-       
-               private synchronized IMolecule 
maximumStructure(List<IAtomContainer> mcsslist) {
-                       int maxmcss = -99999999;
-                       IAtomContainer maxac = null;
-                       int fragment = 1;
-                       if (mcsslist == null || mcsslist.size() == 0) return 
null;
-                       for (IAtomContainer a: mcsslist) {
-                               if (a.getAtomCount() > maxmcss) {
-                                       maxmcss = a.getAtomCount();
-                                       maxac = a;
-                               }
-                       }
-                       return new Molecule(maxac);
-               }
-
-               public IAtomContainer get() { 
-                       if (innerMcss == null)
-                               return call();
-                       else
-                               return innerMcss;
-               }
-       }
 }

Modified: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/SMARTSSearchTask.java
===================================================================
--- 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/SMARTSSearchTask.java    
    2013-02-15 22:35:56 UTC (rev 31125)
+++ 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tasks/SMARTSSearchTask.java    
    2013-02-19 18:44:38 UTC (rev 31126)
@@ -118,7 +118,7 @@
                        try {
                                SMARTSQueryTool queryTool = new 
SMARTSQueryTool(searchString);
                                for (Compound compound: cList) {
-                                       boolean status = 
queryTool.matches(compound.getIMolecule());
+                                       boolean status = 
queryTool.matches(compound.getIAtomContainer());
                                        if (status && queryTool.countMatches() 
> 0)
                                                matches.add(compound);
                                }

Added: csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/Fragment.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/Fragment.java   
                        (rev 0)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/Fragment.java   
2013-02-19 18:44:38 UTC (rev 31126)
@@ -0,0 +1,110 @@
+
+/* 
+ * Copyright (C) 2009-2013 Syed Asad Rahman <[email protected]>
+ *
+ * Contact: [email protected]
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1
+ * of the License, or (at your option) any later version.
+ * All we ask is that proper credit is given for our work, which includes
+ * - but is not limited to - adding the above copyright notice to the beginning
+ * of your source code files, and to any copyright notice that you may 
distribute
+ * with programs based on this work.
+ *
+ * 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 Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+package tools.mcss;
+
+import java.util.BitSet;
+import org.openscience.cdk.exception.CDKException;
+import org.openscience.cdk.fingerprint.ShortestPathFingerprinter;
+import org.openscience.cdk.interfaces.IAtomContainer;
+
+/**
+ *
+ * @author Syed Asad Rahman <[email protected]>
+ *
+ */
+final public class Fragment implements Comparable<Fragment> {
+
+    public synchronized IAtomContainer getContainer() {
+        return container;
+    }
+    private BitSet fingerprint;
+    private long fingerprintAsLong;
+    private final IAtomContainer container;
+
+    public Fragment(IAtomContainer container) throws CDKException {
+        if (container == null) {
+            throw new CDKException("NULL container not supported");
+        }
+        ShortestPathFingerprinter spf = new ShortestPathFingerprinter(1024);
+        this.container = container;
+        this.fingerprint = spf.getBitFingerprint(container).asBitSet();
+        this.fingerprintAsLong = convert(this.fingerprint);
+    }
+
+    @Override
+    public synchronized boolean equals(Object obj) {
+        if (obj == null) {
+            return false;
+        }
+        if (getClass() != obj.getClass()) {
+            return false;
+        }
+        final Fragment other = (Fragment) obj;
+
+        if (this.container != other.container && (this.container == null || 
(this.container.getAtomCount() != other.container.getAtomCount()))) {
+            return false;
+        }
+
+        if (this.fingerprint != other.fingerprint && (this.fingerprint == null 
|| !this.fingerprint.equals(other.fingerprint))) {
+            return false;
+        }
+        if (this.fingerprintAsLong != other.fingerprintAsLong) {
+            return false;
+        }
+
+        return true;
+    }
+
+    @Override
+    public synchronized int hashCode() {
+        int hash = 3;
+        hash = 47 * hash + (this.fingerprint != null ? 
this.fingerprint.hashCode() : 0);
+        hash = 47 * hash + (int) (this.fingerprintAsLong ^ 
(this.fingerprintAsLong >>> 32));
+        return hash;
+    }
+
+    @Override
+    public synchronized int compareTo(Fragment t) {
+
+        if (this.fingerprintAsLong == t.fingerprintAsLong) {
+            return 0;
+        } else if (this.fingerprintAsLong > t.fingerprintAsLong) {
+            return 1;
+        } else {
+            return -1;
+        }
+    }
+
+    private synchronized long convert(BitSet bits) {
+        long value = 0L;
+        if (bits == null || bits.isEmpty()) {
+            return value;
+        }
+        for (int i = 0; i < bits.length(); ++i) {
+            value += bits.get(i) ? (1L << i) : 0L;
+        }
+        return value;
+    }
+}

Added: csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/JobType.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/JobType.java    
                        (rev 0)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/JobType.java    
2013-02-19 18:44:38 UTC (rev 31126)
@@ -0,0 +1,46 @@
+/*
+ * To change this template, choose Tools | Templates
+ * and open the template in the editor.
+ */
+package tools.mcss;
+
+/**
+ *
+ * @author Asad
+ */
+public enum JobType implements Comparable<JobType> {
+
+    /**
+     * Default MCS algorithm.
+     */
+    MCS(0, "MCS search"),
+    /**
+     * Substructure search algorithm.
+     */
+    Substructure(1, "Substructure search");
+    private final int type;
+    private final String description;
+
+    JobType(int aStatus, String desc) {
+        this.type = aStatus;
+        this.description = desc;
+    }
+
+    /**
+     * Returns type of algorithm.
+     *
+     * @return type of algorithm
+     */
+    public int type() {
+        return this.type;
+    }
+
+    /**
+     * Returns short description of the algorithm.
+     *
+     * @return description of the algorithm
+     */
+    public String description() {
+        return this.description;
+    }
+}

Added: csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSS.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSS.java       
                        (rev 0)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSS.java       
2013-02-19 18:44:38 UTC (rev 31126)
@@ -0,0 +1,141 @@
+/**
+ * Copyright (C) 2009-2013 Syed Asad Rahman <[email protected]>
+ *
+ * Contact: [email protected]
+ *
+ * This program is free software; you can redistribute it and/or modify it 
under the terms of the GNU Lesser General
+ * Public License as published by the Free Software Foundation; either version 
2.1 of the License, or (at your option)
+ * any later version. All we ask is that proper credit is given for our work, 
which includes - but is not limited to -
+ * adding the above copyright notice to the beginning of your source code 
files, and to any copyright notice that you
+ * may distribute with programs based on this work.
+ *
+ * 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 Lesser General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License 
along with this program; if not, write to
+ * the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 
02110-1301 USA.
+ */
+package tools.mcss;
+
+import cmd.AtomContainerComparator;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.Future;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import org.openscience.cdk.interfaces.IAtomContainer;
+
+/**
+ *
+ * @author Syed Asad Rahman <[email protected]>
+ *
+ */
+final public class MCSS {
+
+    private final List<IAtomContainer> calculateMCSS;
+    private TaskUpdater updater;
+    private double percentDone = 0.01;
+
+    public MCSS(List<IAtomContainer> jobList, JobType jobType, TaskUpdater 
updater, int numberOfThreads) {
+        this.updater = updater;
+        int threadsAvailable = Runtime.getRuntime().availableProcessors() - 1;
+        if (numberOfThreads > 0) {
+            threadsAvailable = numberOfThreads;
+        }
+                               if (updater != null) 
updater.updateStatus("Calculating MCSS using "+threadsAvailable+" threads");
+        Comparator<IAtomContainer> comparator = new AtomContainerComparator();
+        Collections.sort(jobList, comparator);
+        calculateMCSS = calculateMCSS(jobList, jobType, threadsAvailable);
+    }
+
+    private synchronized List<IAtomContainer> 
calculateMCSS(List<IAtomContainer> mcssList, JobType jobType, int nThreads) {
+        if (updater != null) {
+            updater.setTotalCount(mcssList.size());
+            updater.incrementCount();
+        }
+
+        List<IAtomContainer> newMCSSList = Collections.synchronizedList(new 
ArrayList<IAtomContainer>(nThreads));
+        if (nThreads == 1) {
+            MCSSThread task = new MCSSThread(mcssList, jobType, updater, 1);
+            List<IAtomContainer> results = task.call();
+            if (results != null) {
+                newMCSSList.addAll(results);
+            }
+            return newMCSSList;
+        } else {
+            /*
+             * Calling recursive MCS
+             */
+            newMCSSList = submitMultiThreadedJob(mcssList, jobType, updater, 
nThreads);
+            while (newMCSSList.size() > 1) {
+                if (newMCSSList.size() > 2) {
+                    newMCSSList = submitMultiThreadedJob(newMCSSList, jobType, 
updater, nThreads);
+                } else {
+                    newMCSSList = submitMultiThreadedJob(newMCSSList, jobType, 
updater, 1);
+                }
+            }
+        }
+        return newMCSSList;
+    }
+
+    /**
+     * @return the calculateMCSS
+     */
+    public synchronized List<IAtomContainer> getCalculateMCSS() {
+        return Collections.unmodifiableList(calculateMCSS);
+    }
+
+    private synchronized List<IAtomContainer> 
submitMultiThreadedJob(List<IAtomContainer> mcssList, 
+                                                                     JobType 
jobType, TaskUpdater updater, int nThreads) {
+        int taskNumber = 1;
+        List<IAtomContainer> newMCSSList = Collections.synchronizedList(new 
ArrayList<IAtomContainer>(nThreads));
+        List<Future<List<IAtomContainer>>> futureList = new 
ArrayList<Future<List<IAtomContainer>>>();
+        ExecutorService threadPool = Executors.newFixedThreadPool(nThreads);
+        int step = (int) Math.ceil((double) mcssList.size() / (double) 
nThreads);
+        if (step < 2) {
+            step = 2; // Can't have a step size of less than 2
+        }
+        for (int i = 0; i < mcssList.size(); i += step) {
+            int endPoint = i + step;
+            if (endPoint > mcssList.size()) {
+                endPoint = mcssList.size();
+            }
+            List<IAtomContainer> subList = new 
ArrayList<IAtomContainer>(mcssList.subList(i, endPoint));
+            if (subList.size() > 1) {
+                MCSSThread mcssJobThread = new MCSSThread(subList, jobType, 
updater, taskNumber++);
+                Future<List<IAtomContainer>> callMCSSThread = 
threadPool.submit(mcssJobThread);
+                futureList.add(callMCSSThread);
+            } else {
+                newMCSSList.add(subList.get(0));
+            }
+        }
+
+        for (Future<List<IAtomContainer>> results : futureList) {
+
+            if (results == null) {
+                continue;
+            }
+            try {
+                List<IAtomContainer> f = results.get();
+                if (f != null) {
+                    newMCSSList.addAll(results.get());
+                }
+            } catch (Exception e) {
+                
Logger.getLogger(MCSSThread.class.getName()).log(Level.WARNING, "Execution 
exception: {0}", e);
+            }
+
+        }
+
+        threadPool.shutdown();
+        return newMCSSList;
+    }
+
+    public synchronized String getTitle() {
+        return "Calculating Maximum Commmon Substrutures (MCSS)";
+    }
+}

Added: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSSThread.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSSThread.java 
                        (rev 0)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/MCSSThread.java 
2013-02-19 18:44:38 UTC (rev 31126)
@@ -0,0 +1,149 @@
+/**
+ * Copyright (C) 2009-2013 Syed Asad Rahman <[email protected]>
+ *
+ * Contact: [email protected]
+ *
+ * This program is free software; you can redistribute it and/or modify it 
under the terms of the GNU Lesser General
+ * Public License as published by the Free Software Foundation; either version 
2.1 of the License, or (at your option)
+ * any later version. All we ask is that proper credit is given for our work, 
which includes - but is not limited to -
+ * adding the above copyright notice to the beginning of your source code 
files, and to any copyright notice that you
+ * may distribute with programs based on this work.
+ *
+ * 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 Lesser General Public License for more
+ * details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License 
along with this program; if not, write to
+ * the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 
02110-1301 USA.
+ */
+package tools.mcss;
+
+import java.util.*;
+import java.util.concurrent.Callable;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import org.openscience.cdk.exception.CDKException;
+import org.openscience.cdk.interfaces.IAtomContainer;
+import org.openscience.cdk.smiles.SmilesGenerator;
+import org.openscience.cdk.tools.manipulator.AtomContainerManipulator;
+import org.openscience.smsd.AtomAtomMapping;
+import org.openscience.smsd.BaseMapping;
+import org.openscience.smsd.Isomorphism;
+import org.openscience.smsd.Substructure;
+import org.openscience.smsd.interfaces.Algorithm;
+
+/**
+ *
+ * @author Syed Asad Rahman <[email protected]>
+ *
+ */
+final public class MCSSThread implements Callable<List<IAtomContainer>> {
+
+    private final List<IAtomContainer> mcssList;
+    private final JobType jobType;
+    private int taskNumber = 0;
+    private TaskUpdater updater = null;
+
+    /**
+     *
+     * @param mcssList
+     * @param jobType MCS/Substructure
+     * @param taskNumber
+     */
+    public MCSSThread(List<IAtomContainer> mcssList, JobType jobType, 
TaskUpdater updater, int taskNumber) {
+        this.mcssList = mcssList;
+        this.jobType = jobType;
+        this.taskNumber = taskNumber;
+        this.updater = updater;
+    }
+
+    @Override
+    public synchronized List<IAtomContainer> call() {
+
+//        System.out.println("Calling MCSSTask " + taskNumber + " with " + 
mcssList.size() + " items");
+        List<IAtomContainer> resultsList = new ArrayList<IAtomContainer>();
+        long startTime = Calendar.getInstance().getTimeInMillis();
+        IAtomContainer querySeed = 
AtomContainerManipulator.removeHydrogens(mcssList.get(0));
+        long calcTime = startTime;
+
+
+        try {
+            for (int index = 1; index < mcssList.size(); index++) {
+                IAtomContainer target = 
AtomContainerManipulator.removeHydrogens(mcssList.get(index));
+                Collection<Fragment> fragmentsFomMCS;
+                if (this.jobType == JobType.MCS) {
+                    Isomorphism comparison = new Isomorphism(querySeed, 
target, Algorithm.DEFAULT, true, true);
+                    comparison.setChemFilters(true, true, true);
+                    fragmentsFomMCS = getMCSS(comparison);
+                } else {
+                    Substructure comparison = new Substructure(querySeed, 
target, true, true, false);
+                    comparison.setChemFilters(true, true, true);
+                    fragmentsFomMCS = getMCSS(comparison);
+                }
+//                System.out.println("MCSS for task " + taskNumber + " has " + 
querySeed.getAtomCount() + " atoms, and " + querySeed.getBondCount() + " 
bonds");
+//                System.out.println("Target for task " + taskNumber + " has " 
+ target.getAtomCount() + " atoms, and " + target.getBondCount() + " bonds");
+
+
+                long endCalcTime = Calendar.getInstance().getTimeInMillis();
+//                System.out.println("Task " + taskNumber + " index " + index 
+ " took " + (endCalcTime - calcTime) + "ms");
+                calcTime = endCalcTime;
+
+                if (querySeed == null || querySeed.getAtomCount() == 0) {
+                    break;
+                }
+//                System.out.println("comparison for task " + taskNumber + " 
has " + fragmentsFomMCS.size()
+//                        + " unique matches of size " + 
comparison.getFirstAtomMapping().getCount());
+                querySeed = fragmentsFomMCS.iterator().next().getContainer();
+                if (updater != null) updater.incrementCount();
+            }
+
+        } catch (Exception e) {
+            Logger.getLogger(MCSSThread.class.getName()).log(Level.SEVERE, 
null, e);
+            if (updater != null) 
updater.logException(MCSSThread.class.getName(),Level.SEVERE, null, e);
+        }
+        if (resultsList != null) {
+            resultsList.add(querySeed);
+        }
+
+        long endTime = Calendar.getInstance().getTimeInMillis();
+//        System.out.print("Done: task " + taskNumber + " took " + (endTime - 
startTime) + "ms");
+//        System.out.println(" and mcss has " + querySeed.getAtomCount() + " 
atoms, and " + querySeed.getBondCount() + " bonds");
+        return resultsList;
+    }
+
+    private synchronized Collection<Fragment> getMCSS(BaseMapping comparison) {
+        Set<Fragment> matchList = new HashSet<Fragment>();
+        // System.out.println("Found "+comparison.getAllAtomMapping().size()+" 
mappings");
+        for (AtomAtomMapping mapping : comparison.getAllAtomMapping()) {
+            //IAtomContainer match = getMatchedSubgraph(mol1, 
mapping.getMappings());
+            IAtomContainer match;
+            try {
+                match = mapping.getCommonFragmentInQuery();
+                try {
+                    matchList.add(new Fragment(match));
+                } catch (CDKException ex) {
+                    
Logger.getLogger(MCSSThread.class.getName()).log(Level.SEVERE, null, ex);
+                    if (updater != null) 
updater.logException(MCSSThread.class.getName(),Level.SEVERE, null, ex);
+                }
+            } catch (CloneNotSupportedException ex) {
+                Logger.getLogger(MCSSThread.class.getName()).log(Level.SEVERE, 
null, ex);
+                if (updater != null) 
updater.logException(MCSSThread.class.getName(),Level.SEVERE, null, ex);
+            }
+            // System.out.println("match has "+match.getAtomCount()+" atoms, 
and "+match.getBondCount()+" bonds");
+        }
+
+        return matchList;
+    }
+
+    /**
+     * Return SMILES
+     *
+     * @param ac
+     * @return
+     */
+    public synchronized String getMCSSSmiles(IAtomContainer ac) {
+        SmilesGenerator g = new SmilesGenerator();
+        g.setUseAromaticityFlag(true);
+        return g.createSMILES(ac);
+    }
+}

Added: 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/TaskUpdater.java
===================================================================
--- 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/TaskUpdater.java    
                            (rev 0)
+++ 
csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/tools/mcss/TaskUpdater.java    
    2013-02-19 18:44:38 UTC (rev 31126)
@@ -0,0 +1,42 @@
+/*
+ * To change this template, choose Tools | Templates
+ * and open the template in the editor.
+ */
+package tools.mcss;
+
+import java.util.logging.Level;
+
+/**
+ *
+ * @author Scooter
+ */
+public interface TaskUpdater {
+
+       /**
+        * Set the number of iterations.
+        *
+        * @param nIterations
+        **/
+       public void setTotalCount(int nIterations);
+
+       /**
+        * Update the count
+        **/
+       public void incrementCount();
+
+       /**
+        * Update the status message
+        **/
+       public void updateStatus(String status);
+
+       /**
+        * This logs an exception and provides a mechanism
+        * for tools to integrate with the caller's logging mechanism
+        *
+        * @param className the class name of the reporter
+        * @param level the level of the error
+        * @param message the log message
+        * @param exception the exception itself
+        */
+       public void logException(String className, Level level, String message, 
Exception exception);
+}

Modified: csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/ui/CompoundTable.java
===================================================================
--- csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/ui/CompoundTable.java      
2013-02-15 22:35:56 UTC (rev 31125)
+++ csplugins/trunk/ucsf/scooter/chemViz/src/chemViz/ui/CompoundTable.java      
2013-02-19 18:44:38 UTC (rev 31126)
@@ -395,7 +395,7 @@
                        try {
                                SMARTSQueryTool queryTool = new 
SMARTSQueryTool(smartsQuery);
                                for (Compound compound: compoundList) {
-                                       boolean status = 
queryTool.matches(compound.getIMolecule());
+                                       boolean status = 
queryTool.matches(compound.getIAtomContainer());
                                        if (status && queryTool.countMatches() 
> 0)
                                                matches.add(compound);
                                }

-- 
You received this message because you are subscribed to the Google Groups 
"cytoscape-cvs" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/cytoscape-cvs?hl=en.
For more options, visit https://groups.google.com/groups/opt_out.


Reply via email to