diff --git a/interfaces/cython/cantera/ck2cti.py b/interfaces/cython/cantera/ck2cti.py index 849cd7ce8..4bec765c7 100644 --- a/interfaces/cython/cantera/ck2cti.py +++ b/interfaces/cython/cantera/ck2cti.py @@ -1001,16 +1001,18 @@ class Parser(object): return species, thermo, composition, note def setupKinetics(self): - self.valid_tokens = dict((k,'species') for k in self.speciesDict) - self.valid_tokens.update(('(+%s)' % k, 'falloff3b: %s' % k) for k in self.speciesDict) - self.valid_tokens['M'] = 'third-body' - self.valid_tokens['m'] = 'third-body' - self.valid_tokens['(+M)'] = 'falloff3b' - self.valid_tokens['(+m)'] = 'falloff3b' - self.valid_tokens['<=>'] = 'equal' - self.valid_tokens['=>'] = 'equal' - self.valid_tokens['='] = 'equal' - self.Slen = max(map(len, self.valid_tokens)) + # We look for species including the next permissible character. '\n' is + # appended to the reaction string to identify the last species in the + # reaction string. Checking this character is necessary to correctly + # identify species with names ending in '+' or '='. + self.species_tokens = set() + for next_char in ('<','=','(','+','\n'): + self.species_tokens.update(k + next_char for k in self.speciesDict) + self.other_tokens = {'M': 'third-body', 'm': 'third-body', + '(+M)': 'falloff3b', '(+m)': 'falloff3b', + '<=>': 'equal', '=>': 'equal', '=': 'equal'} + self.other_tokens.update(('(+%s)' % k, 'falloff3b: %s' % k) for k in self.speciesDict) + self.Slen = max(map(len, self.other_tokens)) def readKineticsEntry(self, entry): """ @@ -1048,17 +1050,26 @@ class Parser(object): A = float(tokens[-3]) b = float(tokens[-2]) Ea = float(tokens[-1]) - reaction = ''.join(tokens[:-3]) + reaction = ''.join(tokens[:-3]) + '\n' - # Identify tokens comprising the reaction expression. Look for the - # longest possible sub-sequences first. + # Identify species tokens in the reaction expression in order of + # decreasing length locs = {} for i in range(self.Slen, 0, -1): for j in range(len(reaction)-i+1): test = reaction[j:j+i] - if test in self.valid_tokens: + if test in self.species_tokens: + reaction = reaction[:j] + ' '*(i-1) + reaction[j+i-1:] + locs[j] = test[:-1], 'species' + + # Identify other tokens in the reaction expression in order of + # descending length + for i in range(self.Slen, 0, -1): + for j in range(len(reaction)-i+1): + test = reaction[j:j+i] + if test in self.other_tokens: reaction = reaction[:j] + ' '*i + reaction[j+i:] - locs[j] = test, self.valid_tokens[test] + locs[j] = test, self.other_tokens[test] # Anything that's left should be a stoichiometric coefficient or a '+' # between species diff --git a/interfaces/cython/cantera/test/test_convert.py b/interfaces/cython/cantera/test/test_convert.py index a62a5f3a7..bb9f4c36a 100644 --- a/interfaces/cython/cantera/test/test_convert.py +++ b/interfaces/cython/cantera/test/test_convert.py @@ -131,19 +131,22 @@ class chemkinConverterTest(utilities.CanteraTest): outName='species-names.cti', quiet=True) gas = ct.Solution('species-names.cti') - self.assertEqual(gas.n_species, 5) + self.assertEqual(gas.n_species, 6) self.assertEqual(gas.species_name(0), '(Parens)') self.assertEqual(gas.species_name(1), '@#$%^-2') self.assertEqual(gas.species_name(2), '[xy2]*{.}') self.assertEqual(gas.species_name(3), 'plus+') self.assertEqual(gas.species_name(4), 'eq=uals') + self.assertEqual(gas.species_name(5), 'plus') - self.assertEqual(gas.n_reactions, 4) + self.assertEqual(gas.n_reactions, 6) nu = gas.product_stoich_coeffs() - gas.reactant_stoich_coeffs() - self.assertEqual(list(nu[:,0]), [-1, -1, 2, 0, 0]) - self.assertEqual(list(nu[:,1]), [-2, 3, -1, 0, 0]) - self.assertEqual(list(nu[:,2]), [-1, 0, 0, 1, 0]) - self.assertEqual(list(nu[:,3]), [3, 0, 0, -2, -1]) + self.assertEqual(list(nu[:,0]), [-1, -1, 2, 0, 0, 0]) + self.assertEqual(list(nu[:,1]), [-2, 3, -1, 0, 0, 0]) + self.assertEqual(list(nu[:,2]), [-1, 0, 0, 1, 0, 0]) + self.assertEqual(list(nu[:,3]), [3, 0, 0, -2, -1, 0]) + self.assertEqual(list(nu[:,4]), [2, 0, 0, -1, 0, -1]) + self.assertEqual(list(nu[:,5]), [1, 0, 0, 1, -1, -1]) def test_unterminatedSections(self): self.assertRaises(ck2cti.InputParseError, diff --git a/test/data/species-names.inp b/test/data/species-names.inp index 706cb81dc..3216efe8e 100644 --- a/test/data/species-names.inp +++ b/test/data/species-names.inp @@ -2,7 +2,7 @@ Elements H C End SPEC -(Parens) @#$%^-2 [xy2]*{.} plus+ eq=uals +(Parens) @#$%^-2 [xy2]*{.} plus+ eq=uals plus end thermo @@ -23,6 +23,10 @@ plus+ C 1H 4 G 200.000 3500.000 1000.000 1 7.48514950E-02 1.33909467E-02-5.73285809E-06 1.22292535E-09-1.01815230E-13 2 -9.46834459E+03 1.84373180E+01 5.14987613E+00-1.36709788E-02 4.91800599E-05 3 -4.84743026E-08 1.66693956E-11-1.02466476E+04-4.64130376E+00 4 +plus C 1H 4 G 200.000 3500.000 1000.000 1 + 7.48514950E-02 1.33909467E-02-5.73285809E-06 1.22292535E-09-1.01815230E-13 2 +-9.46834459E+03 1.84373180E+01 5.14987613E+00-1.36709788E-02 4.91800599E-05 3 +-4.84743026E-08 1.66693956E-11-1.02466476E+04-4.64130376E+00 4 eq=uals C 1H 4 G 200.000 3500.000 1000.000 1 7.48514950E-02 1.33909467E-02-5.73285809E-06 1.22292535E-09-1.01815230E-13 2 -9.46834459E+03 1.84373180E+01 5.14987613E+00-1.36709788E-02 4.91800599E-05 3 @@ -34,5 +38,7 @@ end 2(Parens) + [xy2]*{.} = 3@#$%^-2 5.4321e10 1.0 500.0 plus+ + (Parens) = 2plus+ 9.999e9 9.9 999.9 2 plus+ + eq=uals = 3(Parens) 9.999e9 9.9 999.9 +plus + plus+ = 2 (Parens) 9.999e9 9.9 999.9 +plus+ eq=uals = plus++(Parens) 9.999e9 9.9 999.9 end