diff --git a/docs/conf.py b/docs/conf.py index fffe8bf..534d3b8 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -45,18 +45,18 @@ master_doc = 'index' # General information about the project. -project = u'TRuML' -copyright = u'2017, Ryan Suderman' -author = u'Ryan Suderman' +project = 'TRuML' +copyright = '2017, Ryan Suderman' +author = 'Ryan Suderman' # The version info for the project you're documenting, acts as replacement for # |version| and |release|, also used in various other places throughout the # built documents. # # The short X.Y version. -version = u'0.1.0' +version = '0.1.0' # The full version, including alpha/beta/rc tags. -release = u'0.1.0' +release = '0.1.0' # The language for content autogenerated by Sphinx. Refer to documentation # for a list of supported languages. @@ -141,8 +141,8 @@ # (source start file, target name, title, # author, documentclass [howto, manual, or own class]). latex_documents = [ - (master_doc, 'TRuML.tex', u'TRuML Documentation', - u'Ryan Suderman', 'manual'), + (master_doc, 'TRuML.tex', 'TRuML Documentation', + 'Ryan Suderman', 'manual'), ] @@ -151,7 +151,7 @@ # One entry per manual page. List of tuples # (source start file, name, description, authors, manual section). man_pages = [ - (master_doc, 'truml', u'TRuML Documentation', + (master_doc, 'truml', 'TRuML Documentation', [author], 1) ] @@ -162,7 +162,7 @@ # (source start file, target name, title, author, # dir menu entry, description, category) texinfo_documents = [ - (master_doc, 'TRuML', u'TRuML Documentation', + (master_doc, 'TRuML', 'TRuML Documentation', author, 'TRuML', 'One line description of project.', 'Miscellaneous'), ] diff --git a/tests/test_actions.py b/tests/test_actions.py index a9fb185..239ae2b 100644 --- a/tests/test_actions.py +++ b/tests/test_actions.py @@ -67,7 +67,7 @@ def test_interface_map(self): idm0 = self.m7.interface_diff_map(self.m9) assert len(idm0) == 1 s0 = objects.Site('a', 1) - assert s0 in idm0.keys() + assert s0 in list(idm0.keys()) assert idm0[s0] == (-1, objects.Bond(1)) def test_build_mol_map(self): @@ -75,14 +75,14 @@ def test_build_mol_map(self): r0_rhs_mols = utils.flatten_pattern([self.p3]) mmap0 = objects.Rule._build_mol_map(r0_lhs_mols, r0_rhs_mols) assert mmap0[0] is None - assert len(mmap0.keys()) == 1 + assert len(list(mmap0.keys())) == 1 r1_lhs_mols = utils.flatten_pattern([self.p5, self.p6]) r1_rhs_mols = utils.flatten_pattern([self.p7]) mmap1 = objects.Rule._build_mol_map(r1_lhs_mols, r1_rhs_mols) assert mmap1[0] == 0 assert mmap1[1] == 1 - assert len(mmap1.keys()) == 2 + assert len(list(mmap1.keys())) == 2 r2_lhs_mols = utils.flatten_pattern([self.p4, self.p2, self.p3]) r2_rhs_mols = utils.flatten_pattern([self.p4, self.p3]) diff --git a/tests/test_convert.py b/tests/test_convert.py index a0d1c2e..c2917c8 100644 --- a/tests/test_convert.py +++ b/tests/test_convert.py @@ -1,4 +1,5 @@ from .context import readers +import os class TestConvert: @@ -7,8 +8,9 @@ def __init__(self): @classmethod def setup_class(cls): - test0 = "resources/test0.bngl" - test1 = "resources/test1.bngl" + testdir = os.path.abspath(os.path.dirname(__file__)) + test0 = os.path.join(testdir, "resources/test0.bngl") + test1 = os.path.join(testdir, "resources/test1.bngl") cls.bm0 = readers.BNGLReader(test0).parse() cls.bm1 = readers.BNGLReader(test1).parse() @@ -37,5 +39,5 @@ def test_bmodel0_convert(self): def test_bmodel1_convert(self): krules = [r for rule in self.bm1.rules for r in rule.convert()] - print '\n'.join([r.write_as_kappa() for r in krules]) + print('\n'.join([r.write_as_kappa() for r in krules])) assert len(krules) == 29 diff --git a/tests/test_misc.py b/tests/test_misc.py index b15731c..299eb0c 100644 --- a/tests/test_misc.py +++ b/tests/test_misc.py @@ -90,7 +90,7 @@ def test_graph_builder(self): graph = readers.BNGLReader.parse_cpattern(self.pattern, [self.md0, self.md1])._build_graph() assert len(graph.nodes()) == 3 assert len(graph.edges()) == 2 - assert graph.node[1]['name'] == 'A:xb_yb' + assert graph.nodes[1]['name'] == 'A:xb_yb' assert graph[0][1]['name'] == 'x-x' graph2 = readers.BNGLReader.parse_cpattern(self.pattern2, [self.md2, self.md3])._build_graph() @@ -129,7 +129,7 @@ def test_contains_variable(self): assert self.rate2.contains_variable('rate') def test_factors(self): - print self.rule6._unique_reactant_indices() + print(self.rule6._unique_reactant_indices()) assert self.rule6._unique_reactant_indices() == {0: 2} assert self.rule6.rate_factor(True) == 0.5 - assert self.rule6.rate_factor(False) == 2.0 \ No newline at end of file + assert self.rule6.rate_factor(False) == 2.0 diff --git a/tests/test_parse.py b/tests/test_parse.py index cc8cc9d..91a3456 100644 --- a/tests/test_parse.py +++ b/tests/test_parse.py @@ -63,20 +63,20 @@ def test_rule_parse(self): assert len(rule4s) == 1 assert rule4s[0].rev rule5s = readers.KappaReader.parse_rule(self.rule5, mds) - print rule5s[0] + print(rule5s[0]) assert len(rule5s[0].lhs) == 1 assert len(rule5s[0].lhs[0]) == 1 assert rule5s[0].lhs[0][0] == objects.PlaceHolderMolecule() assert rule5s[0].rev rule6s = readers.KappaReader.parse_rule(self.rule6, mds) - print rule6s + print(rule6s) assert len(rule6s[0].rhs) == 1 assert len(rule6s[0].rhs[0]) == 1 assert rule6s[0].rhs[0][0] == objects.PlaceHolderMolecule() assert rule6s[0].delmol rule7s = readers.KappaReader.parse_rule(self.rule7, mds) assert len(rule7s[0].rhs) == 2 - print rule7s[0].rhs + print(rule7s[0].rhs) assert isinstance(rule7s[0].rhs[1][0], objects.PlaceHolderMolecule) def test_cpattern_parse(self): @@ -200,7 +200,7 @@ def test_mol_parse(self): assert mol1.write_as_bngl() == "Mol(a,b~U,b~P)" mol2 = readers.BNGLReader.parse_molecule(self.mol2, [pmdef3]) assert mol2.write_as_bngl() == "Mol(a,b~?!+)" - print mol2.write_as_kappa() + print(mol2.write_as_kappa()) assert mol2.write_as_kappa() == "Mol(a[.],b{#}[_])" @raises(rbexceptions.NotAMoleculeException) diff --git a/tests/test_print.py b/tests/test_print.py index fc2a5c2..c175666 100644 --- a/tests/test_print.py +++ b/tests/test_print.py @@ -206,6 +206,7 @@ def test_rule(self): assert self.rule6.write_as_kappa() == r"B(b[.]),B(b[.]) -> B(b[1]),B(b[1]) @ 3 * 0.5" assert self.rule6.write_as_bngl() == r"B(b)+B(b) -> B(b!1).B(b!1) 3 * 2.0" assert self.rule6.write_as_bngl(dot=True) == r"B(b).B(b) -> B(b!1).B(b!1) 3 * 2.0" + print(self.rule7.write_as_kappa()) assert self.rule7.write_as_kappa() == r"B(b[1]),B(b[1]) -> B(b[.]),. @ 3 * 0.5" assert self.rule7.write_as_bngl() == r"B(b!1).B(b!1) -> B(b) 3 * 2.0" assert self.rule8.write_as_bngl() == r"B(b) -> B(b)+B(b) 3" @@ -218,9 +219,9 @@ def test_molecule_conversion_determinism(self): assert x[i - 1] < x[i] def test_rule_expansion(self): - print self.rule3.write_as_bngl(from_bngl=True) + print(self.rule3.write_as_bngl(from_bngl=True)) x = self.rule3.convert() - print '\n'.join(sorted([y.write_as_kappa() for y in set(x)])) + print('\n'.join(sorted([y.write_as_kappa() for y in set(x)]))) assert len(x) == 36 def test_obs(self): diff --git a/truml/objects.py b/truml/objects.py index 02129c8..5879623 100644 --- a/truml/objects.py +++ b/truml/objects.py @@ -6,8 +6,8 @@ import logging import networkx as nx import networkx.algorithms.isomorphism as iso -import rbexceptions -import utils +from . import rbexceptions +from . import utils from copy import deepcopy from math import factorial @@ -67,9 +67,9 @@ def __init__(self, n, sds, snm, hss=False): def _invert_site_name_map(self): """Builds a dictionary of BNGL site names to a list of Kappa site names""" self.inv_site_name_map = {} - for k in self.site_name_map.keys(): + for k in list(self.site_name_map.keys()): v = self.site_name_map[k] - if v not in self.inv_site_name_map.keys(): + if v not in list(self.inv_site_name_map.keys()): self.inv_site_name_map[v] = [k] else: self.inv_site_name_map[v].append(k) @@ -78,7 +78,7 @@ def convert(self): """Converts MoleculeDef to use Kappa-compatible site names if necessary""" ss = [] snm = {} - k_track = {s: list(reversed(sorted(self.inv_site_name_map[s]))) for s in self.inv_site_name_map.keys()} + k_track = {s: list(reversed(sorted(self.inv_site_name_map[s]))) for s in list(self.inv_site_name_map.keys())} for s in self.sites: name = k_track[s.name].pop() ss.append(SiteDef(name, s.state_list)) @@ -342,28 +342,28 @@ def rename_sites(names, site, idcs): return tuple([rename_site(name, site, index) for name, index in zip(names, idcs)]) # Check for the possibility of overlapping patterns - possible_overlap = {k: False for k in un_configs_per_site.keys()} - for k in un_configs_per_site.keys(): + possible_overlap = {k: False for k in list(un_configs_per_site.keys())} + for k in sorted(list(un_configs_per_site.keys())): num_identical_sites = len(self.mdef.inv_site_name_map[k]) - if num_identical_sites > 1 and k in un_configs_per_site.keys(): - num_present_sites = sum([len(idcs) for idcs in un_configs_per_site[k].values()]) + if num_identical_sites > 1 and k in list(un_configs_per_site.keys()): + num_present_sites = sum([len(idcs) for idcs in list(un_configs_per_site[k].values())]) if num_identical_sites > num_present_sites >= 1: possible_overlap[k] = True break k_configs = {} - for sn in un_configs_per_site.keys(): + for sn in list(un_configs_per_site.keys()): k_configs[sn] = [] k_sn_names = set(self.mdef.inv_site_name_map[sn]) cur_combs = [] - for s, idcs in un_configs_per_site[sn].iteritems(): + for s, idcs in un_configs_per_site[sn].items(): if len(cur_combs) == 0: cur_combs = [rename_sites(names, s, idcs) for names in it.combinations(k_sn_names, len(idcs))] else: tmp_combs = [] for cc in cur_combs: - rem_names = k_sn_names - set(map(lambda l: l.name, cc)) + rem_names = k_sn_names - set([l.name for l in cc]) new_combs = [rename_sites(names, s, idcs) for names in it.combinations(rem_names, len(idcs))] for nc in new_combs: tmp_combs.append(cc + nc) @@ -371,14 +371,14 @@ def rename_sites(names, site, idcs): if possible_overlap[sn]: need_state = self._site_state_present(un_configs_per_site[sn]) - num_rem_sites = len(self.mdef.inv_site_name_map[k]) - sum([len(idcs) for idcs in un_configs_per_site[sn].values()]) - indices = range(len(self.sites), len(self.sites) + num_rem_sites) + num_rem_sites = len(self.mdef.inv_site_name_map[k]) - sum([len(idcs) for idcs in list(un_configs_per_site[sn].values())]) + indices = list(range(len(self.sites), len(self.sites) + num_rem_sites)) for idx in indices: possible_sites = self._enumerate_site(sn, idx, need_state) tmp_combs = [] for cc in cur_combs: - rem_names = k_sn_names - set(map(lambda l: l.name, cc)) + rem_names = k_sn_names - set([l.name for l in cc]) new_combs = [rename_site(x, y, idx) for x, y in it.product(rem_names, possible_sites)] for nc in new_combs: tmp_combs.append(cc + (nc,)) @@ -386,7 +386,7 @@ def rename_sites(names, site, idcs): k_configs[sn] = cur_combs - k_prod = it.product(*k_configs.values()) + k_prod = it.product(*list(k_configs.values())) return sorted([Molecule(self.name, [e for t in tt for e in sorted(t)], self.mdef) for tt in k_prod]) @@ -452,7 +452,7 @@ def interface_diff_map(self, other): if len(used_other_idcs) < len(other.sites): return None # there are unmatched sites in other else: - return {k: v for k, v in imap.iteritems() if v != (-1, -1)} + return {k: v for k, v in imap.items() if v != (-1, -1)} def _write(self, bngl=True): """ @@ -786,14 +786,14 @@ def _permute(g): # dict of all (node name, node list) pairs node_name_dict = {} for node in g.nodes(): - name = g.node[node]['name'] - if name not in node_name_dict.keys(): + name = g.nodes[node]['name'] + if name not in list(node_name_dict.keys()): node_name_dict[name] = [node] else: node_name_dict[name].append(node) # Remove nodes with unique names - for n in node_name_dict.keys(): + for n in list(node_name_dict.keys()): if len(node_name_dict[n]) == 1: node_name_dict.pop(n) else: @@ -801,14 +801,14 @@ def _permute(g): # Find all permutations of all node types (possible node mappings) per_node_tuples = [] - for n in node_name_dict.keys(): + for n in list(node_name_dict.keys()): op = node_name_dict[n] # Original permutation of node type n perms = list(it.permutations(op)) # All permutations of node type n # Convert each permutation into a list of tuples. The list is a # mapping from the original ordering to a permutation. Tuples is a # list of these lists of tuples for each permutation of node type n - tuples = [list(it.izip(op, p)) for p in perms] + tuples = [list(zip(op, p)) for p in perms] per_node_tuples.append(tuples) # First take the Cartesian product over the list of lists of @@ -855,7 +855,7 @@ def automorphisms(self): em = iso.categorical_edge_match('name', '') for gp in self._permute(g): is_iso = iso.is_isomorphic(g, gp, edge_match=em, node_match=nm) - equal_edges = set(g.edges()) == set(gp.edges()) + equal_edges = set([frozenset(x) for x in g.edges]) == set([frozenset(x) for x in gp.edges()]) # Automorphisms require that a permutation of a graph's nodes # is both isomorphic to the original graph and that the # permutation's edges are preserved from the original graph @@ -963,7 +963,7 @@ def convert(self): c_cps = [] for cp in self.cpatterns: c_cps.append(cp.convert()) - return list(it.imap(lambda p: CPatternList(list(p)), it.product(*c_cps))) + return list(map(lambda p: CPatternList(list(p)), it.product(*c_cps))) def write_as_bngl(self, dot): all_placeholder = True @@ -1067,7 +1067,7 @@ def __init__(self, n, v): def write_as_bngl(self, namespace=dict()): """Writes Parameter as BNGL string""" - bname = namespace[self.name] if self.name in namespace.keys() else self.name + bname = namespace[self.name] if self.name in list(namespace.keys()) else self.name val = self.value.write_as_bngl(namespace) if isinstance(self.value, Expression) else self.value return '%s %s' % (bname, val) @@ -1100,7 +1100,7 @@ def write_as_bngl(self, namespace=dict()): """Writes Expression as BNGL string""" conv_atom_list = [] for atom in self.atom_list: - if atom in namespace.keys(): + if atom in list(namespace.keys()): conv_atom_list.append(namespace[atom]) else: conv_atom_list.append(atom) @@ -1113,7 +1113,7 @@ def write_as_kappa(self): i = 0 while (i < len(self.atom_list)): a = self.atom_list[i] - if a in bngl_to_kappa_func_map.keys(): + if a in list(bngl_to_kappa_func_map.keys()): trig_func_match = re.compile('sinh|cosh|tanh|asinh|acosh|atanh') if re.match('log', a) or re.match(trig_func_match, a): expr.append(bngl_to_kappa_func_map[a](self.atom_list[i + 2])) @@ -1153,7 +1153,7 @@ def __init__(self, name, expr): def write_as_bngl(self, namespace=dict()): """Writes function as BNGL string""" - bname = namespace[self.name] if self.name in namespace.keys() else self.name + bname = namespace[self.name] if self.name in list(namespace.keys()) else self.name return '%s=%s' % (bname, self.expr.write_as_bngl(namespace)) def write_as_kappa(self, as_obs=True): @@ -1215,7 +1215,7 @@ def write_as_bngl(self, namespace=dict()): try: return self.rate.write_as_bngl(namespace) except AttributeError: - if isinstance(self.rate, str) and self.rate in namespace.keys(): + if isinstance(self.rate, str) and self.rate in list(namespace.keys()): return namespace[self.rate] else: return str(self.rate) @@ -1280,7 +1280,7 @@ def __init__(self, lhs, rhs, rate, rev=False, rev_rate=None, label=None, delmol= def _placeholder_check(self): if len(self.lhs_mols) != len(self.rhs_mols): return True - elif None in self.mol_map.values(): + elif None in list(self.mol_map.values()): return True elif set(range(len(self.rhs_mols))) != set(self.mol_map.values()): return True @@ -1301,7 +1301,7 @@ def insert_placeholders(self): else: rhs_list.append(PlaceHolderMolecule()) # Update Molecule to CPattern mapping to accommodate new Molecule (and CPattern) - if len(rmol2cp.keys()) < li + 1: + if len(list(rmol2cp.keys())) < li + 1: rmol2cp[li] = li else: for ri in reversed(sorted(rmol2cp.keys())): @@ -1312,7 +1312,7 @@ def insert_placeholders(self): if ri < li: break - mapped_rhs_idcs = set(it.ifilterfalse(lambda l: l is None, self.mol_map.values())) + mapped_rhs_idcs = set(l for l in self.mol_map.values() if l is not None) unmapped_rhs_idcs = set(range(len(self.rhs_mols))) - mapped_rhs_idcs maxi = len(lmol2cp) @@ -1326,9 +1326,9 @@ def insert_placeholders(self): rhs_list.append(self.rhs_mols[ri]) lhs_cps, rhs_cps = {v: [] for v in set(lmol2cp.values())}, {v: [] for v in set(rmol2cp.values())} - for i in lmol2cp.keys(): + for i in list(lmol2cp.keys()): lhs_cps[lmol2cp[i]].append(lhs_list[i]) - for i in rmol2cp.keys(): + for i in list(rmol2cp.keys()): rhs_cps[rmol2cp[i]].append(rhs_list[i]) self.lhs = CPatternList([CPattern(lhs_cps[k]) for k in sorted(lhs_cps.keys())]) @@ -1419,7 +1419,7 @@ def _build_actions(self, rev=False): smap = lhs_mols[i].interface_diff_map(rhs_mols[i]) mdef = lhs_mols[i].mdef - for k in smap.keys(): + for k in list(smap.keys()): diff = smap[k] if diff[0] != -1 and diff[1] != -1: action_list.append(BondAndStateChange(i, k, diff[0], diff[1], mdef)) @@ -1475,7 +1475,7 @@ def rate_factor(self, b2k): reactant_counts = self._unique_reactant_indices() if reactant_counts: multiple_reactant_factor = 1 - for k, v in reactant_counts.iteritems(): + for k, v in reactant_counts.items(): multiple_reactant_factor *= factorial(v) factor = auto_factor * multiple_reactant_factor @@ -1567,8 +1567,8 @@ def _calc_factor(cp): else: un_configs_per_site[bngl_site_name][bngl_site] += 1 m_int_symm = 1 - for d in un_configs_per_site.values(): - for n in d.values(): + for d in list(un_configs_per_site.values()): + for n in list(d.values()): m_int_symm *= factorial(n) f *= m_int_symm return f @@ -1579,7 +1579,7 @@ def _ftos(self, cp): def write_as_bngl(self, namespace=dict()): """Writes Observable as BNGL string""" - bname = namespace[self.name] if self.name in namespace.keys() else self.name + bname = namespace[self.name] if self.name in list(namespace.keys()) else self.name return "%s %s %s" % (self.type, bname, ' '.join([p.write_as_bngl() for p in self.cpatterns])) def write_as_kappa(self): diff --git a/truml/parsers.py b/truml/parsers.py index a03d42b..c99cf42 100644 --- a/truml/parsers.py +++ b/truml/parsers.py @@ -1,5 +1,5 @@ -from objects import Bond -from rbexceptions import NotCompatibleException +from .objects import Bond +from .rbexceptions import NotCompatibleException import pyparsing as pp import re diff --git a/truml/readers.py b/truml/readers.py index 834b346..3ffca35 100644 --- a/truml/readers.py +++ b/truml/readers.py @@ -2,14 +2,14 @@ from deepdiff import DeepDiff -from objects import * -from parsers import KappaParser, BNGLParser +from .objects import * +from .parsers import KappaParser, BNGLParser import itertools as it import logging import pyparsing as pp import re -import utils +from . import utils class Reader(object): @@ -57,7 +57,7 @@ def __init__(self, file_name=None): file_name : str """ super(KappaReader, self).__init__(file_name) - self.lines = list(it.ifilterfalse(self.ignore_line, [re.sub('//.*$', '', l).strip() for l in self.lines])) + self.lines = [re.sub('//.*$', '', l).strip() for l in self.lines if not self.ignore_line(l)] # var_dict keeps track of read variables and observables and what type they are # Variables can be constant values (c), patterns (p), or dynamic expressions (d) self.var_dict = {} @@ -105,7 +105,7 @@ def parse(self): "Exact conversion of observable '%s' to BNGL is not possible. Renamed to '%s'" % ( name, bname)) - if bname in model.convert_namespace.values(): + if bname in list(model.convert_namespace.values()): rebname = bname + '_' logging.warning( "Name '%s' already exists due to inexact conversion. Renamed to '%s'" % (bname, rebname)) @@ -120,7 +120,7 @@ def parse(self): self.var_dict[name] = 'p' else: pat_dict, subst_expr_list = self.get_var_patterns(expr_list) - for p in pat_dict.keys(): + for p in list(pat_dict.keys()): model.add_obs(Observable(p, self.parse_cpatterns(pat_dict[p].strip('|'), model.molecules))) self.var_dict[p] = 'p' model.add_func(Function(name, Expression(subst_expr_list))) @@ -157,7 +157,7 @@ def var_is_dynamic_no_pat(self, expr_list): for atom in expr_list: if re.match('\[T', atom): return True - for k, v in self.var_dict.iteritems(): + for k, v in self.var_dict.items(): if re.match("%s" % k, atom) and (v == 'd' or v == 'p'): return True return False @@ -532,7 +532,8 @@ def __init__(self, file_name=None): """ super(BNGLReader, self).__init__(file_name) self.lines = self.condense_line_continuation( - it.ifilterfalse(self.ignore_line, [re.sub('#.*$', '', l).strip() for l in self.lines])) + [re.sub('#.*$', '', l).strip() for l in self.lines + if not self.ignore_line(l)]) self.is_def_block = False self.is_init_block = False @@ -584,7 +585,7 @@ def parse(self): for i, l in enumerate(self.lines): - if re.match('\s*\n', l): + if re.match('$|\s*\n', l): continue logging.debug("Parsing %s" % l.strip()) @@ -689,7 +690,7 @@ def _get_molecdef(m): raise rbexceptions.NotCompatibleException("Kappa does not allow states to start with digits. " "Please rename states in BNGL file") - if sd.name in site_name_counter.keys(): + if sd.name in list(site_name_counter.keys()): site_name_counter[sd.name] += 1 if not has_site_symmetry: logging.info('SiteDef %s has site symmetry' % sd.name) @@ -697,12 +698,12 @@ def _get_molecdef(m): else: site_name_counter[sd.name] = 1 - for sn in site_name_counter.keys(): + for sn in list(site_name_counter.keys()): if site_name_counter[sn] == 1: site_name_counter.pop(sn) site_name_map[sn] = sn - for sn in site_name_counter.keys(): + for sn in list(site_name_counter.keys()): while site_name_counter[sn] > 0: site_name_map[sn + str(site_name_counter[sn] - 1)] = sn site_name_counter[sn] -= 1 @@ -908,7 +909,7 @@ def _has_intramolecular_binding(lhs_cp, rhs_cp): """ d = DeepDiff(lhs_cp, rhs_cp) try: - changed = d.get('type_changes').keys() + changed = list(d.get('type_changes').keys()) except AttributeError: return False num_changed_bonds = 0 diff --git a/truml/truml.py b/truml/truml.py index cfc9749..473a8f2 100644 --- a/truml/truml.py +++ b/truml/truml.py @@ -6,8 +6,8 @@ import argparse as ap import logging -import rbexceptions -import readers +from . import rbexceptions +from . import readers import re import pyparsing as pp @@ -51,7 +51,7 @@ def main(): model = kr.parse() except pp.ParseException as pe: logging.error("Could not parse line: %s" % pe.line) - print "Could not parse line: '%s'. Exiting" % pe.line + print("Could not parse line: '%s'. Exiting" % pe.line) exit(1) model.write_as_bngl(re.sub('ka', 'bngl', kf), args.dot_and_plus) else: @@ -61,6 +61,6 @@ def main(): model = br.parse() except pp.ParseException as pe: logging.error("Could not parse line: %s" % pe.line) - print "Could not parse line: '%s'. Exiting" % pe.line + print("Could not parse line: '%s'. Exiting" % pe.line) exit(1) model.write_as_kappa(re.sub('bngl', 'ka', bf), args.no_print_funcs)