def test_rmg_reaction(self): test_reaction = RMGReaction( reactants=[RMGMolecule(SMILES="CC"), RMGMolecule(SMILES="[O]O")], products=[RMGMolecule(SMILES="[CH2]C"), RMGMolecule(SMILES="OO")]) self.assertTrue( test_reaction.isIsomorphic(self.reaction.get_rmg_reaction())) self.assertTrue( test_reaction.isIsomorphic(self.reaction2.get_rmg_reaction()))
def testRemoveIsotopeForReactions(self): """ Test that remove isotope algorithm works with Reaction objects. """ eth = Species().fromAdjacencyList( """ 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """ ) ethi = Species().fromAdjacencyList( """ 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 i13 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """ ) unlabeledRxn = Reaction(reactants=[eth], products = [eth]) labeledRxn = Reaction(reactants=[ethi], products = [ethi]) stripped = remove_isotope(labeledRxn) self.assertTrue(unlabeledRxn.isIsomorphic(stripped))
def testRemoveIsotopeForReactions(self): """ Test that remove isotope algorithm works with Reaction objects. """ eth = Species().fromAdjacencyList(""" 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """) ethi = Species().fromAdjacencyList(""" 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 i13 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """) unlabeledRxn = Reaction(reactants=[eth], products=[eth]) labeledRxn = Reaction(reactants=[ethi], products=[ethi]) stripped = remove_isotope(labeledRxn) self.assertTrue(unlabeledRxn.isIsomorphic(stripped))
def test_labeled_reaction(self): test_reaction = RMGReaction( reactants=[RMGMolecule(SMILES="CC"), RMGMolecule(SMILES="[O]O")], products=[RMGMolecule(SMILES="[CH2]C"), RMGMolecule(SMILES="OO")]) labeled_reaction, reaction_family = self.reaction.get_labeled_reaction( ) self.assertEquals(reaction_family.lower(), "h_abstraction") self.assertTrue(test_reaction.isIsomorphic(labeled_reaction)) merged = labeled_reaction.reactants[0].merge( labeled_reaction.reactants[1]) self.assertTrue(merged.getLabeledAtom("*1").isCarbon()) self.assertTrue(merged.getLabeledAtom("*2").isHydrogen()) self.assertTrue(merged.getLabeledAtom("*3").isOxygen) merged = labeled_reaction.products[0].merge( labeled_reaction.products[1]) self.assertTrue(merged.getLabeledAtom("*3").isCarbon()) self.assertTrue(merged.getLabeledAtom("*2").isHydrogen()) self.assertTrue(merged.getLabeledAtom("*1").isOxygen) labeled_reaction, reaction_family = self.reaction2.get_labeled_reaction( ) self.assertEquals(reaction_family.lower(), "h_abstraction") self.assertTrue(test_reaction.isIsomorphic(labeled_reaction)) merged = labeled_reaction.reactants[0].merge( labeled_reaction.reactants[1]) self.assertTrue(merged.getLabeledAtom("*1").isCarbon()) self.assertTrue(merged.getLabeledAtom("*2").isHydrogen()) self.assertTrue(merged.getLabeledAtom("*3").isOxygen) merged = labeled_reaction.products[0].merge( labeled_reaction.products[1]) self.assertTrue(merged.getLabeledAtom("*3").isCarbon()) self.assertTrue(merged.getLabeledAtom("*2").isHydrogen()) self.assertTrue(merged.getLabeledAtom("*1").isOxygen)
def testInplaceRemoveIsotopeForReactions(self): """ Test that removeIsotope and redoIsotope works with reactions """ eth = Species().fromAdjacencyList( """ 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """ ) ethi = Species().fromAdjacencyList( """ 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 i13 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """ ) unlabeledRxn = Reaction(reactants=[eth], products = [eth]) labeledRxn = Reaction(reactants=[ethi], products = [ethi]) storedLabeledRxn = labeledRxn.copy() modifiedAtoms = remove_isotope(labeledRxn, inplace=True) self.assertTrue(unlabeledRxn.isIsomorphic(labeledRxn)) redo_isotope(modifiedAtoms) self.assertTrue(storedLabeledRxn.isIsomorphic(labeledRxn))
def testInplaceRemoveIsotopeForReactions(self): """ Test that removeIsotope and redoIsotope works with reactions """ eth = Species().fromAdjacencyList(""" 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """) ethi = Species().fromAdjacencyList(""" 1 C u0 p0 c0 {2,S} {3,S} {4,S} {5,S} 2 C u0 p0 c0 i13 {1,S} {6,S} {7,S} {8,S} 3 H u0 p0 c0 {1,S} 4 H u0 p0 c0 {1,S} 5 H u0 p0 c0 {1,S} 6 H u0 p0 c0 {2,S} 7 H u0 p0 c0 {2,S} 8 H u0 p0 c0 {2,S} """) unlabeledRxn = Reaction(reactants=[eth], products=[eth]) labeledRxn = Reaction(reactants=[ethi], products=[ethi]) storedLabeledRxn = labeledRxn.copy() modifiedAtoms = remove_isotope(labeledRxn, inplace=True) self.assertTrue(unlabeledRxn.isIsomorphic(labeledRxn)) redo_isotope(modifiedAtoms) self.assertTrue(storedLabeledRxn.isIsomorphic(labeledRxn))
rSpecies1.generateResonanceIsomers() pSpecies1.generateResonanceIsomers() testReaction = Reaction(reactants=[rSpecies1], products=[pSpecies1], reversible=True) reactionList = [] for moleculeA in rSpecies1.molecule: tempList = rmg_database.kinetics.generateReactionsFromFamilies( [moleculeA], [], only_families=['intra_H_migration']) for rxn0 in tempList: reactionList.append(rxn0) gotOne = False for reaction in reactionList: # Check if any of the RMG proposed reactions matches the reaction in the mechanism if testReaction.isIsomorphic(reaction): # Now add the labeled atoms to the Molecule, and check all labels were added atLblsR = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) atLblsP = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) for reactant in reaction.reactants: #reactant = reactant.molecule[0] reactant.clearLabeledAtoms() for atom in reactant.atoms: for atomLabel in reaction.labeledAtoms: if atom == atomLabel[1]: atom.label = atomLabel[0] atLblsR[atomLabel[0]] = True for product in reaction.products: #product = product.molecule[0] product.clearLabeledAtoms()
def validate_irc(self, calc=None): """ A method to verify an IRC calc """ assert "irc" in calc.label, "The calculator provided is not an IRC calculator" reaction_label = calc.label.split("_irc")[0] logging.info("Validating IRC file...") irc_path = os.path.join(calc.scratch, calc.label + ".log") if not os.path.exists(irc_path): logging.info("It seems that the IRC claculation has not been run.") return False f = open(irc_path, "r") file_lines = f.readlines()[-5:] completed = False for file_line in file_lines: if "Normal termination" in file_line: logging.info("IRC successfully ran") completed = True if not completed: logging.info("IRC failed... could not be validated...") return False pth1 = list() steps = list() with open(irc_path) as outputFile: for line in outputFile: line = line.strip() if line.startswith('Point Number:'): if int(line.split()[2]) > 0: if int(line.split()[-1]) == 1: ptNum = int(line.split()[2]) pth1.append(ptNum) else: pass elif line.startswith('# OF STEPS ='): numStp = int(line.split()[-1]) steps.append(numStp) # This indexes the coordinate to be used from the parsing if steps == []: logging.error('No steps taken in the IRC calculation!') return False else: pth1End = sum(steps[:pth1[-1]]) # Compare the reactants and products ircParse = ccread(irc_path) # cf. # http://cclib.sourceforge.net/wiki/index.php/Using_cclib#Additional_information atomcoords = ircParse.atomcoords atomnos = ircParse.atomnos # Convert the IRC geometries into RMG molecules # We don't know which is reactant or product, so take the two at the end of the # paths and compare to the reactants and products mol1 = RMGMolecule() mol1.fromXYZ(atomnos, atomcoords[pth1End]) mol2 = RMGMolecule() mol2.fromXYZ(atomnos, atomcoords[-1]) testReaction = RMGReaction( reactants=mol1.split(), products=mol2.split(), ) r, p = reaction_label.split("_") reactants = [] products = [] for react in r.split("+"): react = RMGMolecule(SMILES=react) reactants.append(react) for prod in p.split("+"): prod = RMGMolecule(SMILES=prod) products.append(prod) possible_reactants = [] possible_products = [] for reactant in reactants: possible_reactants.append( reactant.generate_resonance_structures()) for product in products: possible_products.append( product.generate_resonance_structures()) possible_reactants = list(itertools.product(*possible_reactants)) possible_products = list(itertools.product(*possible_products)) for possible_reactant in possible_reactants: reactant_list = [] for react in possible_reactant: reactant_list.append(react.toSingleBonds()) for possible_product in possible_products: product_list = [] for prod in possible_product: product_list.append(prod.toSingleBonds()) targetReaction = RMGReaction(reactants=list(reactant_list), products=list(product_list)) if targetReaction.isIsomorphic(testReaction): logging.info("IRC calculation was successful!") return True logging.info("IRC calculation failed for {} :(".format(calc.label)) return False
def validate_irc(self): # TODO: need to add more verification here logging.info("Validating IRC file...") irc_path = os.path.join(self.irc_calc.scratch, self.irc_calc.label + ".log") if not os.path.exists(irc_path): logging.info( "It seems that the file was `fixed`, reading in the `fixed` version.") irc_path = irc_path.replace("left", "(").replace("right", ")") if not os.path.exists(irc_path): logging.info( "It seems that the IRC claculation has not been run.") return False f = open(irc_path, "r") file_lines = f.readlines()[-5:] completed = False for file_line in file_lines: if " Normal termination" in file_line: logging.info("IRC successfully ran") completed = True if completed == False: logging.info("IRC failed... could not be validated...") return False pth1 = list() steps = list() with open(irc_path) as outputFile: for line in outputFile: line = line.strip() if line.startswith('Point Number:'): if int(line.split()[2]) > 0: if int(line.split()[-1]) == 1: ptNum = int(line.split()[2]) pth1.append(ptNum) else: pass elif line.startswith('# OF STEPS ='): numStp = int(line.split()[-1]) steps.append(numStp) # This indexes the coordinate to be used from the parsing if steps == []: logging.error('No steps taken in the IRC calculation!') return False else: pth1End = sum(steps[:pth1[-1]]) # Compare the reactants and products ircParse = ccread(irc_path) # cf. http://cclib.sourceforge.net/wiki/index.php/Using_cclib#Additional_information atomcoords = ircParse.atomcoords atomnos = ircParse.atomnos # Convert the IRC geometries into RMG molecules # We don't know which is reactant or product, so take the two at the end of the # paths and compare to the reactants and products mol1 = Molecule() mol1.fromXYZ(atomnos, atomcoords[pth1End]) mol2 = Molecule() mol2.fromXYZ(atomnos, atomcoords[-1]) testReaction = Reaction( reactants=mol1.split(), products=mol2.split(), ) if isinstance(self.reaction.rmg_reaction.reactants[0], rmgpy.molecule.Molecule): targetReaction = Reaction( reactants=[reactant.toSingleBonds() for reactant in self.reaction.rmg_reaction.reactants], products=[product.toSingleBonds() for product in self.reaction.rmg_reaction.products], ) elif isinstance(self.reaction.rmg_reaction.reactants[0], rmgpy.species.Species): targetReaction = Reaction( reactants=[reactant.molecule[0].toSingleBonds() for reactant in self.reaction.rmg_reaction.reactants], products=[product.molecule[0].toSingleBonds() for product in self.reaction.rmg_reaction.products], ) if targetReaction.isIsomorphic(testReaction): return True else: return False
def get_labeled_reaction(self): """ A method that will return a labeled reaction given a reaction label or rmg_reaction A label or an rmg_reaction needs to be provided in order for this method to work. If both are provided, we assert that the label matches the reaction. Variables: - label (str): the reaction label of interest - rmg_reaction (RMGReaction): the reaction of interest Returns: - reaction (RMGReaction): An RMGReaction with labeled reactants and products - name (str): The string corresponding to the reaction family matched to the reaction of interest """ if not (self.rmg_database or self.ts_databases): self.rmg_database, self.ts_databases = self.load_databases() assert (self.label or self.rmg_reaction ), "You must provide a reaction or a reaction label" match = False if self.label: rmg_reactants = [] rmg_products = [] r, p = self.label.split("_") for react in r.split("+"): s = RMGMolecule(SMILES=react) rmg_reactants.append(s) for prod in p.split("+"): s = RMGMolecule(SMILES=prod) rmg_products.append(s) test_reaction = RMGReaction(reactants=rmg_reactants, products=rmg_products) if self.rmg_reaction: assert self.rmg_reaction.isIsomorphic( test_reaction ), "The reaction label provided does not match the RMGReaction provided..." for name, family in list( self.rmg_database.kinetics.families.items()): if match: break try: labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.reactants, test_reaction.products) except ValueError: continue if not (labeled_r and labeled_p): continue if ((len(labeled_r) > 0) and (len(labeled_p) > 0)): logging.info("Matched reaction to {} family".format(name)) labeled_reactants = deepcopy(labeled_r) labeled_products = deepcopy(labeled_p) test_reaction.reactants = labeled_r[:] test_reaction.products = labeled_p[:] match = True final_family = family final_name = name break elif self.rmg_reaction: #RMGReaction but no label rmg_reactants = [] rmg_products = [] for react in self.rmg_reaction.reactants: if isinstance(react, RMGSpecies): rmg_reactants.append(react.molecule) elif isinstance(react, RMGMolecule): rmg_reactants.append([react]) for prod in self.rmg_reaction.products: if isinstance(prod, RMGSpecies): rmg_products.append(prod.molecule) elif isinstance(prod, RMGMolecule): rmg_products.append([prod]) test_reactants = [] test_products = [] if len(rmg_reactants) == 1: for l1 in rmg_reactants[0]: test_reactants.append([l1]) elif len(rmg_reactants) == 2: l1, l2 = rmg_reactants for i in l1: for j in l2: test_reactants.append([i, j]) if len(rmg_products) == 1: for l1 in rmg_products[0]: test_products.append([l1]) elif len(rmg_products) == 2: l1, l2 = rmg_products for i in l1: for j in l2: test_products.append([i, j]) reacts = test_reactants[:] prods = test_products[:] for name, family in list( self.rmg_database.kinetics.families.items()): logging.info("Trying to match {} to {}".format( self.rmg_reaction, family)) if match: continue test_reactants = reacts[:] test_products = prods[:] for test_reactant in test_reactants: for test_product in test_products: if match: continue test_reaction = RMGReaction(reactants=test_reactant, products=test_product) try: labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.reactants, test_reaction.products) if not (labeled_r and labeled_p): logging.info( "Unable to determine a reaction for the forward direction. Trying the reverse direction." ) raise ActionError except (ValueError, ActionError, IndexError): try: # Trying the reverse reaction if the forward reaction doesn't work # This is useful for R_Addition reactions labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.products, test_reaction.reactants) except (ValueError, ActionError, IndexError): continue if not (labeled_r and labeled_p): labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.products, test_reaction.reactants) continue if ((len(labeled_r) > 0) and (len(labeled_p) > 0)) and ( self.rmg_reaction.isIsomorphic(test_reaction)): logging.info( "Matched reaction to {} family".format(name)) labeled_reactants = deepcopy(labeled_r) labeled_products = deepcopy(labeled_p) test_reaction.reactants = labeled_r[:] test_reaction.products = labeled_p[:] logging.info("{}".format(labeled_r)) logging.info("{}".format(labeled_p)) match = True final_family = family print final_family final_name = name assert match, "Could not idetify labeled reactants and products" #try: reaction_list = final_family.generateReactions(test_reaction.reactants, test_reaction.products) #except KeyError: # reaction_list = None # logging.info("For some reason, RMG is having trouble generating reactions for {}".format(test_reaction)) assert reaction_list, "Could not match a reaction to a reaction family..." for reaction in reaction_list: if test_reaction.isIsomorphic(reaction): reaction.reactants = labeled_reactants reaction.products = labeled_products break self.rmg_reaction = reaction self.reaction_family = final_name return self.rmg_reaction, self.reaction_family
def performCalcs(chemkinRxn): logging.info("chemkinRxn: {!r}".format(chemkinRxn)) # Ensure all resonance isomers have been generated logging.info('Ensuring resonance isomers have been generated') for species in itertools.chain(chemkinRxn.reactants, chemkinRxn.products): print(type(species)) species = species.generateResonanceIsomers() testReaction = Reaction(reactants=chemkinRxn.reactants, products=chemkinRxn.products, reversible=True) reactants = [species for species in chemkinRxn.reactants] # reactant_molecules is a list of lists of resonance isomers, # eg. a bimolecular reaction where the second reactant has 2 isomers is: [[r1],[r2i1,r2i2]] products = [species for species in chemkinRxn.products] # products is a list of molecule objects (only one resonance form of each product), eg [p1, p2] print reactants #print type(reactant_molecules[0]) print products checkRxn = rmgDatabase.kinetics.generateReactionsFromFamilies( reactants, products, only_families=rxnFamilies) if len(checkRxn) == 1: logging.info("Generated one reaction:") logging.info(checkRxn) reaction = checkRxn[0] else: # didn't break from for loop for reaction in checkRxn: logging.info("Generated these reactions:") logging.info(reaction) reaction = checkRxn[0] raise Exception( "Couldn't generate exactly one reaction matching {} in family {}". format(chemkinRxn, rxnFamilies)) logging.info("The reaction of interest is as follows: ") logging.info(reaction) logging.info("asserting that the testReaction is Isomorphic") assert testReaction.isIsomorphic(reaction) logging.info("reaction: {!r}".format(reaction)) atLblsR = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) atLblsP = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) gotOne = False logging.info("Labeling reactant atoms") for reactant in reaction.reactants: reactant = reactant reactant.clearLabeledAtoms() for atom in reactant.atoms: for atomLabel in reaction.labeledAtoms: if atom == atomLabel[1]: atom.label = atomLabel[0] atLblsR[atomLabel[0]] = True logging.info("Labeling product atoms") for product in reaction.products: product = product product.clearLabeledAtoms() for atom in product.atoms: for atomLabel in reaction.labeledAtoms: if atom == atomLabel[1]: atom.label = atomLabel[0] atLblsP[atomLabel[0]] = True if all(atLblsR.values()) and all(atLblsP.values()): gotOne = True rxnFamily = reaction.family assert gotOne, "Couldn't label all the atoms using the reaction family template" logging.info( "We have generated a {!s} reaction that matches, and used it to label the atoms." .format(rxnFamily)) logging.info("Calculating reaction kinetics") reaction = calculate(reaction) logging.info("For reaction {0!r}".format(reaction)) if reaction.kinetics: logging.info("We have calculated kinetics {0!r}".format( reaction.kinetics)) else: logging.warning("Couldn't calculate kinetics.") if reaction.kinetics and False: """ Return the rate coefficient in the appropriate combination of cm^3, mol, and s at temperature `T` in K and pressure `P` in Pa. """ importKin = chemkinRxn['rmgPyKinetics'] Temp = 1000 # Kelvin idx = str(i) row = [idx, rxnFamily] row.extend([mol.label for mol in reaction.reactants]) row.extend([mol.label for mol in reaction.products]) rateCal = reaction.calculateTSTRateCoefficient(Temp) row.extend(['AutoTST_fwd', str(rateCal)]) if isinstance(importKin, PDepArrhenius) or isinstance( importKin, PDepKineticsModel): row.extend([ smiles_dict[entry], str(importKin.getRateCoefficient(Temp, 1000000)) ]) #1000000 Pa = 10 bar else: row.extend( [smiles_dict[entry], str(importKin.getRateCoefficient(Temp))]) famDatabase = rmgDatabase.kinetics.families[rxnFamily] famDatabase.addKineticsRulesFromTrainingSet( thermoDatabase=rmgDatabase.thermo) famDatabase.fillKineticsRulesByAveragingUp() # Using the `testReaction` will keep the reaction direction the same as the model rxnTemplate = famDatabase.getReactionTemplate(testReaction) kList = famDatabase.getKinetics(testReaction, rxnTemplate) allRates = [] kComments = [] for rate in kList: k = rate[0] if k: label = rate[1] if isinstance(label, KineticsDepository): label = label.label elif isinstance(label, KineticsRules): label = label.label if label.lower() == 'rate rules': kComments = k.comment.split('\n') allRates.append((label, k.getRateCoefficient(Temp))) kDict = {'Rate Rules': []} for kTuple in allRates: if kTuple[0] == 'AutoTST': kDict['AutoTST'] = kDict['AutoTST'] + [kTuple[1]] elif kTuple[0] == 'rate rules': kDict['Rate Rules'] = kDict['Rate Rules'] + [kTuple[1]] elif kTuple[0].endswith('/NIST'): kDict['NIST'] = kDict['NIST'] + [kTuple[1]] elif kTuple[0].endswith('/rules'): kDict['KineitcsRules'] = kDict['KineitcsRules'] + [kTuple[1]] # Print the values in order kineticsTypes = ['Rate Rules' ] #['AutoTST', 'Rate Rules', 'NIST', 'KineitcsRules'] for kinType in kineticsTypes: row.append(kinType) if kDict[kinType] == []: row.append('no Val') else: for val in kDict[kinType]: row.append(str(val)) # Store line containing reaction from corresponding chemkin file row.append(smiles_dict[entry]) row.append(chemkinRxn['chemkinKinetics'].strip()) # Store rmgpy kinetics group comments row = row + kComments folderPath = os.path.join('KinTxtFiles', idx) if not os.path.exists(folderPath): os.makedirs(folderPath) input_string = ','.join(row) with open( os.path.join(folderPath, smiles_dict[entry] + '_kinetics.txt'), 'w') as kinTxt: kinTxt.write(input_string)
if checkRxn == []: reactIsoms = [mol.generateResonanceIsomers() for mol in reactant_molecules] if len(reactIsoms) == 2: r1, r2 = reactIsoms while checkRxn == []: for moleculeA in r1: for moleculeB in r2: reactant_molecules = [moleculeA, moleculeB] checkRxn = rmgDatabase.kinetics.generateReactionsFromFamilies( reactant_molecules, product_molecules, only_families=chemkinRxn['possibleReactionFamilies']) reaction = checkRxn[0] assert testReaction.isIsomorphic(reaction) # Now add the labeled atoms to the Molecule, and check all labels were added atLblsR = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) atLblsP = dict([(lbl[0], False) for lbl in reaction.labeledAtoms]) gotOne = False for reactant in reaction.reactants: reactant = reactant.molecule[0] reactant.clearLabeledAtoms() for atom in reactant.atoms: for atomLabel in reaction.labeledAtoms: if atom == atomLabel[1]: atom.label = atomLabel[0] atLblsR[atomLabel[0]] = True
def validate_irc(self): """ A method to verify an IRC calc """ logging.info("Validating IRC file...") irc_path = os.path.join( self.directory, "ts", self.conformer.reaction_label, "irc", self.conformer.reaction_label + "_irc_" + self.conformer.direction + "_" + str(self.conformer.index) + ".log") complete, converged = self.verify_output_file(irc_path) if not complete: logging.info("It seems that the IRC claculation did not complete") return False if not converged: logging.info("The IRC calculation did not converge...") return False pth1 = list() steps = list() with open(irc_path) as outputFile: for line in outputFile: line = line.strip() if line.startswith('Point Number:'): if int(line.split()[2]) > 0: if int(line.split()[-1]) == 1: ptNum = int(line.split()[2]) pth1.append(ptNum) else: pass elif line.startswith('# OF STEPS ='): numStp = int(line.split()[-1]) steps.append(numStp) # This indexes the coordinate to be used from the parsing if steps == []: logging.error('No steps taken in the IRC calculation!') return False else: pth1End = sum(steps[:pth1[-1]]) # Compare the reactants and products ircParse = ccread(irc_path) atomcoords = ircParse.atomcoords atomnos = ircParse.atomnos mol1 = RMGMolecule() mol1.fromXYZ(atomnos, atomcoords[pth1End]) mol2 = RMGMolecule() mol2.fromXYZ(atomnos, atomcoords[-1]) testReaction = RMGReaction( reactants=mol1.split(), products=mol2.split(), ) r, p = self.conformer.reaction_label.split("_") reactants = [] products = [] for react in r.split("+"): react = RMGMolecule(SMILES=react) reactants.append(react) for prod in p.split("+"): prod = RMGMolecule(SMILES=prod) products.append(prod) possible_reactants = [] possible_products = [] for reactant in reactants: possible_reactants.append( reactant.generate_resonance_structures()) for product in products: possible_products.append( product.generate_resonance_structures()) possible_reactants = list(itertools.product(*possible_reactants)) possible_products = list(itertools.product(*possible_products)) for possible_reactant in possible_reactants: reactant_list = [] for react in possible_reactant: reactant_list.append(react.toSingleBonds()) for possible_product in possible_products: product_list = [] for prod in possible_product: product_list.append(prod.toSingleBonds()) targetReaction = RMGReaction(reactants=list(reactant_list), products=list(product_list)) if targetReaction.isIsomorphic(testReaction): logging.info("IRC calculation was successful!") return True logging.info("IRC calculation failed for {} :(".format(calc.label)) return False
reactants, products = r.split('=')[0], r.split('=')[1] r1_ID, r2_ID = reactants.split('+') p1_ID, p2_ID = products.split('+')[0], products.split('+')[1] p2_ID = p2_ID.split(')')[0] + ')' rSpecies1 = species_dict_V3[r1_ID] rSpecies2 = species_dict_V3[r2_ID] pSpecies1 = species_dict_V3[p1_ID] pSpecies2 = species_dict_V3[p2_ID] rSpecies1.generateResonanceIsomers() rSpecies2.generateResonanceIsomers() pSpecies1.generateResonanceIsomers() pSpecies2.generateResonanceIsomers() V3_reaction = Reaction(reactants=[rSpecies1, rSpecies2], products=[pSpecies1, pSpecies2], reversible=True) if testReaction.isIsomorphic(V3_reaction): reaction_list_V4[i] = r break else: if 'intra_H_migration' in r: reactants, products = r.split('=')[0], r.split('=')[1] r1_ID = reactants p1_ID = products.split(')')[0] + ')' rSpecies1 = species_dict_V3[r1_ID] pSpecies1 = species_dict_V3[p1_ID] rSpecies1.generateResonanceIsomers() pSpecies1.generateResonanceIsomers() V3_reaction = Reaction(reactants=[rSpecies1], products=[pSpecies1], reversible=True) if testReaction.isIsomorphic(V3_reaction):
def get_labeled_reaction(self, label=None, rmg_reaction=None): """ A method that will return a labeled reaction given a reaction label or rmg_reaction A label or an rmg_reaction needs to be provided in order for this method to work. If both are provided, we assert that the label matches the reaction. Variables: - label (str): the reaction label of interest - rmg_reaction (RMGReaction): the reaction of interest Returns: - reaction (RMGReaction): An RMGReaction with labeled reactants and products - name (str): The string corresponding to the reaction family matched to the reaction of interest """ assert ( label or rmg_reaction), "You must provide a reaction or a reaction label" label_reaction = None rmg_reaction_reaction = None test_reactions = [] match = False if label: rmg_reactants = [] rmg_products = [] r, p = label.split("_") for react in r.split("+"): s = RMGMolecule(SMILES=react) rmg_reactants.append(s) for prod in p.split("+"): s = RMGMolecule(SMILES=prod) rmg_products.append(s) test_reaction = RMGReaction( reactants=rmg_reactants, products=rmg_products) if rmg_reaction: assert rmg_reaction.isIsomorphic( test_reaction), "The reaction label provided does not match the RMGReaction provided..." for name, family in list(self.rmg_database.kinetics.families.items()): if match: break labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.reactants, test_reaction.products) if not (labeled_r and labeled_p): continue if ((len(labeled_r) > 0) and (len(labeled_p) > 0)): logging.info("Matched reaction to {} family".format(name)) labeled_reactants = deepcopy(labeled_r) labeled_products = deepcopy(labeled_p) test_reaction.reactants = labeled_r[:] test_reaction.products = labeled_p[:] match = True final_name = name break elif rmg_reaction: rmg_reactants = [] rmg_products = [] for react in rmg_reaction.reactants: if isinstance(react, RMGSpecies): rmg_reactants.append(react.molecule) elif isinstance(react, RMGMolecule): rmg_reactants.append([react]) for prod in rmg_reaction.products: if isinstance(prod, RMGSpecies): rmg_products.append(prod.molecule) elif isinstance(prod, RMGMolecule): rmg_products.append([prod]) test_reactants = [] test_products = [] if len(rmg_reactants) == 1: test_reactants = rmg_reactants elif len(rmg_reactants) == 2: l1, l2 = rmg_reactants for i in l1: for j in l2: test_reactants.append([i, j]) if len(rmg_products) == 1: test_reactants = rmg_products elif len(rmg_products) == 2: l1, l2 = rmg_products for i in l1: for j in l2: test_products.append([i, j]) for name, family in list(self.rmg_database.kinetics.families.items()): if match: break for test_reactant in test_reactants: for test_products in test_products: if match: continue test_reaction = RMGReaction( reactants=test_reactant, products=test_products) labeled_r, labeled_p = family.getLabeledReactantsAndProducts( test_reaction.reactants, test_reaction.products) if not (labeled_r and labeled_p): continue if ((len(labeled_r) > 0) and (len(labeled_p) > 0)): logging.info( "Matched reaction to {} family".format(name)) labeled_reactants = deepcopy(labeled_r) labeled_products = deepcopy(labeled_p) test_reaction.reactants = labeled_r[:] test_reaction.products = labeled_p[:] logging.info("\n{}".format(labeled_r)) logging.info("\n{}".format(labeled_p)) match = True final_name = name break assert match, "Could not idetify labeled reactants and products" reaction_list = self.rmg_database.kinetics.generate_reactions_from_families( test_reaction.reactants, test_reaction.products, only_families=[final_name]) assert reaction_list, "Could not match a reaction to a reaction family..." for reaction in reaction_list: if test_reaction.isIsomorphic(reaction): reaction.reactants = labeled_reactants reaction.products = labeled_products break return reaction, name