Esempio n. 1
0
def update_molecule(mol, to_single_bonds=False):
    """
    Returns a copy of the current molecule with updated atomTypes
    if to_single_bonds is True, the returned mol contains only single bonds.
    This is useful for isomorphism comparison
    """
    new_mol = Molecule()
    try:
        atoms = mol.atoms
    except AttributeError:
        return None
    atom_mapping = dict()
    for atom1 in atoms:
        new_atom = new_mol.addAtom(Atom(atom1.element))
        atom_mapping[atom1] = new_atom
    for atom1 in atoms:
        for atom2 in atom1.bonds.keys():
            bond_order = 1.0 if to_single_bonds else atom1.bonds[
                atom2].getOrderNum()
            bond = Bond(atom_mapping[atom1], atom_mapping[atom2], bond_order)
            new_mol.addBond(bond)
    try:
        new_mol.updateAtomTypes()
    except AtomTypeError:
        pass
    new_mol.multiplicity = mol.multiplicity
    return new_mol
Esempio n. 2
0
 def testPickle(self):
     """
     Test that a Molecule object can be successfully pickled and
     unpickled with no loss of information.
     """
     molecule0 = Molecule().fromSMILES('C=CC=C[CH2]C')
     molecule0.updateAtomTypes()
     molecule0.updateConnectivityValues()
     import cPickle
     molecule = cPickle.loads(cPickle.dumps(molecule0))
     
     self.assertEqual(len(molecule0.atoms), len(molecule.atoms))
     self.assertEqual(molecule0.getFormula(), molecule.getFormula())
     self.assertTrue(molecule0.isIsomorphic(molecule))
     self.assertTrue(molecule.isIsomorphic(molecule0))
Esempio n. 3
0
    def testPickle(self):
        """
        Test that a Molecule object can be successfully pickled and
        unpickled with no loss of information.
        """
        molecule0 = Molecule().fromSMILES('C=CC=C[CH2]C')
        molecule0.updateAtomTypes()
        molecule0.updateConnectivityValues()
        import cPickle
        molecule = cPickle.loads(cPickle.dumps(molecule0))

        self.assertEqual(len(molecule0.atoms), len(molecule.atoms))
        self.assertEqual(molecule0.getFormula(), molecule.getFormula())
        self.assertTrue(molecule0.isIsomorphic(molecule))
        self.assertTrue(molecule.isIsomorphic(molecule0))
    def getResonanceHybrid(self):
        """
        Returns a molecule object with bond orders that are the average 
        of all the resonance structures.
        """
        # get labeled resonance isomers
        self.generate_resonance_structures(keep_isomorphic=True)

        # only consider reactive molecules as representative structures
        molecules = [mol for mol in self.molecule if mol.reactive]

        # return if no resonance
        if len(molecules) == 1:
            return molecules[0]

        # create a sorted list of atom objects for each resonance structure
        cython.declare(atomsFromStructures = list, oldAtoms = list, newAtoms = list,
                       numResonanceStructures=cython.short, structureNum = cython.short,
                       oldBondOrder = cython.float,
                       index1 = cython.short, index2 = cython.short,
                      newMol=Molecule, oldMol = Molecule,
                      atom1=Atom, atom2=Atom, 
                      bond=Bond,  
                      atoms=list,)

        atomsFromStructures = []
        for newMol in molecules:
            newMol.atoms.sort(key=lambda atom: atom.id)
            atomsFromStructures.append(newMol.atoms)

        numResonanceStructures = len(molecules)

        # make original structure with no bonds
        newMol = Molecule()
        originalAtoms = atomsFromStructures[0]
        for atom1 in originalAtoms:
            atom = newMol.addAtom(Atom(atom1.element))
            atom.id = atom1.id

        newAtoms = newMol.atoms

        # initialize bonds to zero order
        for index1, atom1 in enumerate(originalAtoms):
            for atom2 in atom1.bonds:
                index2 = originalAtoms.index(atom2)
                bond = Bond(newAtoms[index1],newAtoms[index2], 0)
                newMol.addBond(bond)

        # set bonds to the proper value
        for structureNum, oldMol in enumerate(molecules):
            oldAtoms = atomsFromStructures[structureNum]

            for index1, atom1 in enumerate(oldAtoms):
                # make bond orders average of resonance structures
                for atom2 in atom1.bonds:
                    index2 = oldAtoms.index(atom2)

                    newBond = newMol.getBond(newAtoms[index1], newAtoms[index2])
                    oldBondOrder = oldMol.getBond(oldAtoms[index1], oldAtoms[index2]).getOrderNum()
                    newBond.applyAction(('CHANGE_BOND',None,oldBondOrder / numResonanceStructures / 2))
                # set radicals in resonance hybrid to maximum of all structures
                if atom1.radicalElectrons > 0:
                    newAtoms[index1].radicalElectrons = max(atom1.radicalElectrons,
                                                            newAtoms[index1].radicalElectrons)
        newMol.updateAtomTypes(logSpecies = False, raiseException=False)
        return newMol
Esempio n. 5
0
    def getResonanceHybrid(self):
        """
        Returns a molecule object with bond orders that are the average 
        of all the resonance structures.
        """
        # get labeled resonance isomers
        self.generate_resonance_structures(keep_isomorphic=True)

        # only consider reactive molecules as representative structures
        molecules = [mol for mol in self.molecule if mol.reactive]

        # return if no resonance
        if len(molecules) == 1:
            return molecules[0]

        # create a sorted list of atom objects for each resonance structure
        cython.declare(atomsFromStructures = list, oldAtoms = list, newAtoms = list,
                       numResonanceStructures=cython.short, structureNum = cython.short,
                       oldBondOrder = cython.float,
                       index1 = cython.short, index2 = cython.short,
                      newMol=Molecule, oldMol = Molecule,
                      atom1=Atom, atom2=Atom, 
                      bond=Bond,  
                      atoms=list,)

        atomsFromStructures = []
        for newMol in molecules:
            newMol.atoms.sort(key=lambda atom: atom.id)
            atomsFromStructures.append(newMol.atoms)

        numResonanceStructures = len(molecules)

        # make original structure with no bonds
        newMol = Molecule()
        originalAtoms = atomsFromStructures[0]
        for atom1 in originalAtoms:
            atom = newMol.addAtom(Atom(atom1.element))
            atom.id = atom1.id

        newAtoms = newMol.atoms

        # initialize bonds to zero order
        for index1, atom1 in enumerate(originalAtoms):
            for atom2 in atom1.bonds:
                index2 = originalAtoms.index(atom2)
                bond = Bond(newAtoms[index1],newAtoms[index2], 0)
                newMol.addBond(bond)

        # set bonds to the proper value
        for structureNum, oldMol in enumerate(molecules):
            oldAtoms = atomsFromStructures[structureNum]

            for index1, atom1 in enumerate(oldAtoms):
                # make bond orders average of resonance structures
                for atom2 in atom1.bonds:
                    index2 = oldAtoms.index(atom2)

                    newBond = newMol.getBond(newAtoms[index1], newAtoms[index2])
                    oldBondOrder = oldMol.getBond(oldAtoms[index1], oldAtoms[index2]).getOrderNum()
                    newBond.applyAction(('CHANGE_BOND',None,oldBondOrder / numResonanceStructures / 2))
                # set radicals in resonance hybrid to maximum of all structures
                if atom1.radicalElectrons > 0:
                    newAtoms[index1].radicalElectrons = max(atom1.radicalElectrons,
                                                            newAtoms[index1].radicalElectrons)
        newMol.updateAtomTypes(logSpecies = False, raiseException=False)
        return newMol