21import java.util.ArrayList;
22import java.util.Arrays;
23import java.util.Collection;
24import java.util.HashMap;
25import java.util.HashSet;
26import java.util.LinkedHashMap;
30import java.util.logging.Logger;
32import javax.vecmath.Point3d;
34import org.jgrapht.graph.DefaultUndirectedGraph;
35import org.openscience.cdk.interfaces.IAtom;
36import org.openscience.cdk.interfaces.IAtomContainer;
37import org.openscience.cdk.interfaces.IBond;
38import org.openscience.cdk.interfaces.IChemObjectBuilder;
39import org.openscience.cdk.silent.SilentChemObjectBuilder;
41import com.google.gson.Gson;
43import denoptim.constants.DENOPTIMConstants;
44import denoptim.exception.DENOPTIMException;
45import denoptim.graph.Edge.BondType;
46import denoptim.graph.rings.RingClosingAttractor;
47import denoptim.json.DENOPTIMgson;
48import denoptim.utils.MathUtils;
49import denoptim.utils.MoleculeUtils;
50import denoptim.utils.MutationType;
51import denoptim.utils.Randomizer;
65 private List<AttachmentPoint>
lstAPs;
76 private IAtomContainer
mol;
81 private DefaultUndirectedGraph<FragIsomorphNode,FragIsomorphEdge>
94 this.lstAPs =
new ArrayList<AttachmentPoint>();
95 this.lstSymAPs =
new ArrayList<SymmetricAPs>();
96 IChemObjectBuilder builder = SilentChemObjectBuilder.getInstance();
97 this.mol = builder.newAtomContainer();
110 this.lstAPs =
new ArrayList<AttachmentPoint>();
111 this.lstSymAPs =
new ArrayList<SymmetricAPs>();
112 IChemObjectBuilder builder = SilentChemObjectBuilder.getInstance();
113 this.mol = builder.newAtomContainer();
137 this.lstAPs =
new ArrayList<AttachmentPoint>();
138 this.lstSymAPs =
new ArrayList<SymmetricAPs>();
158 if (isomorph !=
null)
161 isomorph.toString());
197 double maxDist = 0.0;
198 Point3d origin =
new Point3d(0,0,0);
199 for (IAtom atm :
atoms())
201 Point3d p = atm.getPoint3d();
212 Point3d p = ap.getDirectionVector();
222 return maxDist > 0.001;
240 IAtomContainer
mol, List<AttachmentPoint> daps)
242 List<SymmetricAPs> lstCompatible =
new ArrayList<>();
243 for (
int i=0; i<daps.size()-1; i++)
249 boolean alreadyFound =
false;
252 if (previousSS.contains(apI))
263 for (
int j=i+1; j<daps.size(); j++)
280 lstCompatible.add(ss);
284 return lstCompatible;
301 IAtom atm1 =
mol.getAtom(a1);
302 IAtom atm2 =
mol.getAtom(a2);
304 if (atm1.getSymbol().compareTo(atm2.getSymbol()) != 0)
308 if (
mol.getConnectedBondsCount(atm1)!=
mol.getConnectedBondsCount(atm2))
312 if (
mol.getConnectedBondsCount(atm1)!=
mol.getConnectedBondsCount(atm2))
315 List<IAtom> la1 =
mol.getConnectedAtomsList(atm2);
316 List<IAtom> la2 =
mol.getConnectedAtomsList(atm2);
319 for (
int i=0; i<la1.size(); i++)
321 IAtom b1 = la1.get(i);
322 for (
int j=0; j<la2.size(); j++)
324 IAtom b2 = la2.get(j);
325 if (b1.getSymbol().compareTo(b2.getSymbol()) == 0)
333 return k == la1.size();
343 public void addAP(
int atomPositionNumber) {
345 addAP(atomPositionNumber,
null, apc);
356 addAP(atomPositionNumber,
null, apClass);
373 atomPositionNumber, dirVec, apClass);
376 IAtom srcAtm =
mol.getAtom(atomPositionNumber);
378 ArrayList<AttachmentPoint> apList =
new ArrayList<>();
406 IAtom srcAtm =
mol.getAtom(srcAtmId);
427 int atmId =
mol.indexOf(srcAtm);
428 return this.
addAP(atmId,
new Point3d(vector.x, vector.y, vector.z), apc);
440 ArrayList<AttachmentPoint> apList =
new ArrayList<>();
454 @SuppressWarnings(
"unchecked")
457 ArrayList<AttachmentPoint> apsOnAtm =
new ArrayList<AttachmentPoint>();
461 apsOnAtm = (ArrayList<AttachmentPoint>) prop;
477 IAtom srcAtm =
mol.getAtom(srcAtmId);
495 ArrayList<AttachmentPoint> apsOnAtm =
497 num = apsOnAtm.size();
513 for (
int atmId = 0; atmId<
mol.getAtomCount(); atmId++)
515 IAtom srcAtm =
mol.getAtom(atmId);
519 for (
int i = 0; i < apsOnAtm.size(); i++)
547 for (IAtom srcAtm :
mol.atoms())
551 ArrayList<AttachmentPoint> apsOnAtm =
574 String allAtomsProp =
"";
597 if (allAtomsProp.trim().equals(
""))
603 for (
int ii=0 ; ii<
mol.getAtomCount(); ii++)
605 IAtom atm =
mol.getAtom(ii);
610 String[] atomsProp = allAtomsProp.split(
612 for (
int i = 0; i< atomsProp.length; i++)
614 String onThisAtm = atomsProp[i];
617 String[] moreAPonThisAtm = onThisAtm.split(
626 for (
int j = 1; j<moreAPonThisAtm.length; j++ )
633 + moreAPonThisAtm[j]);
662 for (
int i = 0; i <
lstAPs.size(); i++)
667 IAtom atm =
mol.getAtom(atmID);
670 ArrayList<AttachmentPoint> oldAPs =
677 ArrayList<AttachmentPoint> aps =
678 new ArrayList<AttachmentPoint>();
697 LinkedHashMap<Integer,List<AttachmentPoint>> apsPerAtom =
698 new LinkedHashMap<>();
699 for (IAtom atm :
mol.atoms())
705 int atmID =
mol.indexOf(atm);
706 ArrayList<AttachmentPoint> apsOnAtm =
710 if (apsPerAtom.containsKey(atmID))
712 apsPerAtom.get(atmID).add(ap);
714 List<AttachmentPoint> lst =
715 new ArrayList<AttachmentPoint>();
717 apsPerAtom.put(atmID,lst);
743 e1.printStackTrace();
751 ap.getAtomPositionNumber(),
752 ap.getDirectionVector(),
755 cAp.
setID(ap.getID());
766 List<SymmetricAPs> cLstSymAPs =
new ArrayList<SymmetricAPs>();
774 cLstSymAPs.add(cSymAPs);
791 for (
int atmPos=0; atmPos<
mol.getAtomCount(); atmPos++)
793 IAtom atm =
mol.getAtom(atmPos);
815 Randomizer rng,
boolean removeUsedRCAs,
boolean rebuild)
845 return mol.getAtom(number);
852 return mol.indexOf(atom);
859 return mol.getAtomCount();
866 return mol.getBondCount();
880 return mol.removeBond(position);
887 return mol.removeBond(atom1, atom2);
894 mol.removeBond(bond);
915 for (IAtom atom :
atoms)
916 mol.removeAtom(atom);
920 for (
int atmId = 0; atmId<
mol.getAtomCount(); atmId++)
922 IAtom srcAtm =
mol.getAtom(atmId);
926 for (
int i = 0; i < apsOnAtm.size(); i++)
945 return mol.getConnectedAtomsList(atom);
952 return mol.getConnectedBondsCount(atom);
971 if (this.mol.getAtomCount() != other.
mol.getAtomCount())
973 reason.append(
"Different atom count (" + this.mol.getAtomCount()
974 +
":" + other.
mol.getAtomCount() +
"); ");
976 if (this.mol.getBondCount() != other.
mol.getBondCount())
978 reason.append(
"Different bond count (" + this.mol.getBondCount()
979 +
":" + other.
mol.getBondCount() +
"); ");
995 public DefaultUndirectedGraph<FragIsomorphNode,FragIsomorphEdge>
1005 Map<IAtom,FragIsomorphNode> atmToNode =
1006 new HashMap<IAtom,FragIsomorphNode>();
1007 Set<IAtom> ignoredDu =
new HashSet<IAtom>();
1008 for (IAtom atm :
mol.atoms())
1012 &&
mol.getConnectedBondsCount(atm)<2)
1019 atmToNode.put(atm,node);
1022 for (IBond bnd :
mol.bonds())
1024 if (bnd.getAtomCount() > 2)
1026 throw new IllegalArgumentException(
"Cannot handle bonds that involve "
1027 +
"more than two atoms");
1029 if (ignoredDu.contains(bnd.getAtom(0))
1030 || ignoredDu.contains(bnd.getAtom(0)))
1038 atmToNode.get(bnd.getAtom(1)), edge);
1046 ap.getAtomPositionNumber())), node, edge);
1102 if (
mol.getAtomCount() > 0)
1130 this.lstSymAPs = sAPs;
1138 if (this.lstSymAPs==
null)
1140 this.lstSymAPs =
new ArrayList<SymmetricAPs>();
1142 this.lstSymAPs.add(symAPs);
1166 List<Vertex> lst =
new ArrayList<Vertex>();
1191 String jsonOutput = gson.toJson(
this);
1215 ap.setOwner(returnedFrag);
1220 return returnedFrag;
General set of constants used in DENOPTIM.
static final String VERTEXJSONTAG
SDF tag containing vertex encoding in JSON format.
static final String ATMPROPAPS
String tag of Atom property used to store attachment points.
static final String APSTAG
SDF tag defining attachment points.
static final String SEPARATORAPPROPAAP
Separator between atom index and APClass in molecular property.
static final String ATMPROPVERTEXID
String tag of Atom property used to store the unique ID of the Vertex corresponding to the molecular ...
static final String SEPARATORAPPROPATMS
Separator between APs on different atoms in molecular property.
static final String DUMMYATMSYMBOL
Symbol of dummy atom.
static final Object ISOMORPHICFAMILYID
Property used to store the identifier of the family of isomorphic fragments that owns a fragment.
static final String SEPARATORAPPROPAPS
Separator between APs on same atom in molecular property.
static final String ATMPROPORIGINALATMID
Name of Atom property used to store the original position of an atom in the atom list of the fragment...
Comparator for DENOPTIMAttachmentPoints.
An attachment point (AP) is a possibility to attach a Vertex onto the vertex holding the AP (i....
APClass getAPClass()
Returns the Attachment Point class.
void setAtomPositionNumber(int atomPositionNumber)
Set the index of the source atom in the list of atoms of the fragment.
int getAtomPositionNumber()
The index of the source atom in the atom list of the fragment.
void setID(int id)
Sets the unique integer that is used to sort list of attachment points.
static String getAPDefinitionsForSDF(LinkedHashMap< Integer, List< AttachmentPoint > > apsPerIndex)
Prepares the two strings that can be used to define AttachmentPoints in SDF files.
Class representing a continuously connected portion of chemical object holding attachment points.
List< Vertex > getMutationSites(List< MutationType > ignoredTypes)
A list of mutation sites from within this vertex.
IBond removeBond(int position)
List< IAtom > getConnectedAtomsList(IAtom atom)
void setSymmetricAPSets(List< SymmetricAPs > sAPs)
int getAPCountOnAtom(int srcAtmId)
Returns the number of APs currently defined on a specific atom source.
List< SymmetricAPs > lstSymAPs
List of AP sets that are related to each other, so that we call them "symmetric" (though symmetry is ...
IAtomContainer mol
Molecular representation of this fragment.
boolean sameAs(Fragment other, StringBuilder reason)
Compares this and another fragment ignoring vertex IDs.
void addAP(int atomPositionNumber)
Adds an attachment point with a dummy APClass.
void removeBond(IBond bond)
AttachmentPoint addAPOnAtom(IAtom srcAtm, APClass apc, Point3d vector)
Add an attachment point to the specifies atom.
List< AttachmentPoint > getCurrentAPs()
Collects APs currently defined as properties of the atoms.
List< AttachmentPoint > getAttachmentPoints()
Fragment(long vertexId)
Constructor for a molecular fragment kind of vertex.
Fragment clone()
Returns a deep copy of this fragments.
Iterable< IAtom > atoms()
ArrayList< AttachmentPoint > getAPsFromAtom(IAtom srcAtm)
IBond removeBond(IAtom atom1, IAtom atom2)
boolean isIsomorphicTo(Vertex other)
Checks for isomorphism of the graph representation of this and another fragment.
void projectPropertyToAP(String allAtomsProp)
Uses a string formatted like the molecular property used for defining attachment points to create the...
IAtom getAtom(int number)
void removeAtom(IAtom atom)
IAtomContainer getIAtomContainer()
DefaultUndirectedGraph< FragIsomorphNode, FragIsomorphEdge > getJGraphFragIsomorphism()
Creates a graph representation of this fragment where both atoms and AttachmentPoints are represented...
Fragment(long vertexId, IAtomContainer mol, BBType bbt, boolean isRCV)
void updateAPs()
Changes the properties of each APs as to reflect the current atom list.
void projectListAPToAtomProperties()
Takes the list of APs from the field of this class and projects the APs into properties of the IAtoms...
static boolean atomsAreCompatible(IAtomContainer mol, int a1, int a2)
Checks if the atoms at the given positions have similar environments i.e.
String toString()
Produces a human readable, short string to represent the vertex by its vertex ID, building block ID (...
void projectAPsToProperties()
Finds the DENOPTIMAttachmentPoint objects defined as properties of the atoms in this container,...
Fragment(long l, IAtomContainer mol, BBType bbt)
Constructor from an atom container, which has APs only as molecular properties.
boolean is3D()
Checks if atoms and APs contained in this fragment have non-zero 3D coordinates.
void updateSymmetryRelations()
Depends on an healthy list of attachment points with properly set pointers to the source atoms.
List< SymmetricAPs > getSymmetricAPSets()
int getAPCountOnAtom(IAtom srcAtm)
Returns the number of APs currently defined on a specific atom source.
static Fragment fromJson(String json)
Reads a JSON string and returns an instance of this class.
void addSymmetricAPSet(SymmetricAPs symAPs)
List< AttachmentPoint > lstAPs
attachment points on this vertex
void removeAP(AttachmentPoint ap)
void addAP(int srcAtmId, APClass apc, Point3d vector)
Add an attachment point to the specifies atom.
static List< SymmetricAPs > identifySymmetryRelatedAPSets(IAtomContainer mol, List< AttachmentPoint > daps)
IAtomContainer getIAtomContainer(Logger logger, Randomizer rng, boolean removeUsedRCAs, boolean rebuild)
Although this type of vertex contains atoms, its content is fixed.
AttachmentPoint addAP(int atomPositionNumber, Point3d dirVec, APClass apClass)
Adds an attachment point.
Fragment()
Constructor of an empty fragment.
IAtom getAtomHoldingAP(AttachmentPoint ap)
Returns the atom where the given attachment point is rooted, i.e., the atom that is involved in the b...
void addAP(int atomPositionNumber, APClass apClass)
Adds an attachment point.
String toJson()
Produces a string that represents this vertex and that adheres to the JSON format.
Fragment(IAtomContainer mol, BBType bbt)
Constructor from another atom container, which has APs only as molecular properties.
Iterable< IBond > bonds()
int getConnectedAtomsCount(IAtom atom)
DefaultUndirectedGraph< FragIsomorphNode, FragIsomorphEdge > jGraphFragIsomorphism
jGraph representation used for detecting fragment isomorphism.
void projectPropertyToAP()
Uses the molecular property defining attachment points to create the DENOPTIMAttachmentPoint objects ...
void removeAtoms(Collection< IAtom > atoms)
Removes a list of atoms and updates the list of attachment points.
boolean isomorphismExists()
Checks if an isomorphism exists between the two fragments.
A collection of AttachmentPoints that are related by a relation that we call "symmetry",...
boolean add(T item)
Adds an item to this list, if not already present.
A vertex is a data structure that has an identity and holds a list of AttachmentPoints.
Set< String > uniquefyingPropertyKeys
List of properties required to make Vertex#sameAs(Vertex, StringBuilder) method return false when pro...
void setMutationTypes(List< MutationType > lst)
List< MutationType > getMutationTypes()
Returns the list of mutation types.
void setProperties(Map< Object, Object > properties)
int getBuildingBlockId()
Returns the index of the building block that should correspond to the position of the building block ...
void setVertexId(long vertexId2)
Vertex.BBType getBuildingBlockType()
List< MutationType > getUnfilteredMutationTypes()
Returns the mutation types that are constitutionally configures for this vertex irrespectively on the...
void setAsRCV(boolean isRCV)
Map< Object, Object > copyStringBasedProperties()
Copies all the string-based properties and properties defined in the Vertex#uniquefyingPropertyKeys s...
boolean sameVertexFeatures(Vertex other, StringBuilder reason)
Compares this and another vertex ignoring vertex IDs.
void setBuildingBlockId(int buildingBlockId)
Object getProperty(Object property)
void setBuildingBlockType(Vertex.BBType buildingBlockType)
void setProperty(Object key, Object property)
long vertexId
Unique identifier associated with the vertex instance.
AttachmentPoint getAP(int i)
Get attachment point i on this vertex.
The RingClosingAttractor represent the available valence/connection that allows to close a ring.
static final Set< APClass > RCAAPCLASSSET
Recognized APClass for RingClosingAttractor.
Class for de/serializing DENOPTIM graphs from/to JSON format.
Some useful math operations.
static double distance(Point3d a, Point3d b)
Calculates distance between point a and point b.
Utilities for molecule conversion.
static void setZeroImplicitHydrogensToAllAtoms(IAtomContainer iac)
Sets zero implicit hydrogen count to all atoms.
static IAtomContainer makeSameAs(IAtomContainer mol)
Constructs a copy of an atom container, i.e., a molecule that reflects the one given in the input arg...
static String getSymbolOrLabel(IAtom atm)
Gets either the elemental symbol (for standard atoms) of the label (for pseudo-atoms).
static int getHeavyAtomCount(IAtomContainer mol)
The heavy atom count.
Tool to generate random numbers and random decisions.
The type of building block.
Flag declaring the type of Vertex implementation.