Commit c602faa2 authored by eladnoor's avatar eladnoor

flake8

parent db56b4e4
Pipeline #48232887 failed with stage
in 19 minutes and 11 seconds
......@@ -27,20 +27,20 @@
from typing import Dict, List, Tuple
from uncertainties import ufloat
import numpy as np
from component_contribution import GibbsEnergyPredictor
from . import (
FARADAY, Compound, R, default_I, default_pH, default_pMg, default_T, ureg)
from . import FARADAY, R, default_I, default_pH, default_pMg, default_T, ureg
from .phased_reaction import PhasedReaction
class ComponentContribution(object):
"""A wrapper class for GibbsEnergyPredictor.
Also holds default conditions for compounds in the different phases.
"""
predictor = GibbsEnergyPredictor()
@ureg.check(None, None, None, '[concentration]', '[temperature]')
......@@ -108,11 +108,12 @@ class ComponentContribution(object):
calculate the confidence interval, use the range -1.96 to 1.96 times
this value
"""
residual_reaction, stored_dg_prime = reaction.separate_stored_dgf_values(
p_h=self.p_h,
ionic_strength=self.ionic_strength,
temperature=self.temperature
)
residual_reaction, stored_dg_prime = \
reaction.separate_stored_dgf_values(
p_h=self.p_h,
ionic_strength=self.ionic_strength,
temperature=self.temperature
)
standard_dg_prime, dg_sigma = \
ComponentContribution.predictor.standard_dg_prime(
......@@ -269,4 +270,6 @@ class ComponentContribution(object):
:param reaction: a PhasedReaction object.
:return: true iff group contribution is needed
"""
return ComponentContribution.predictor.is_using_group_contribution(reaction)
return ComponentContribution.predictor.is_using_group_contribution(
reaction
)
......@@ -356,9 +356,7 @@ class Pathway(object):
rxn = PhasedReaction.parse_formula(row.ReactionFormula,
row.ID,
name_to_compound.get)
if not rxn.is_balanced(fix_protons=True,
fix_water=True,
raise_exception=False):
if not rxn.is_balanced(ignore_atoms=("H")):
warnings.warn(f"Reaction {rxn.rid} is not balanced")
reactions.append(rxn)
if row.ID in reaction_ids:
......
......@@ -28,12 +28,12 @@
from collections import namedtuple
import numpy as np
from equilibrator_cache import Compound
from equilibrator_cache.reaction import Reaction
from equilibrator_cache.thermodynamic_constants import legendre_transform
from . import Q_, R, ccache, ureg
from . import Q_, R, ureg
AQUEOUS_PHASE_NAME = 'aqueous'
GAS_PHASE_NAME = 'gas'
......@@ -90,31 +90,47 @@ PHASED_COMPOUND_DICT = {
standard_dgf=Q_("0 kJ/mol"), num_protons=0, charge=0), # S8
}
class Condition(object):
"""A class for defining the conditions of a compound.
I.e. the phase and the abundance.
"""
def __init__(self, phase: str, abundance: ureg.Quantity = None):
"""Create a new condition object."""
assert phase in PHASE_INFO_DICT, f"Unknown phase: {phase}"
self._phase = phase
self._abundance = abundance or self.standard_abundance
@property
def phase(self) -> str:
"""Return the phase."""
return self._phase
@property
def abundance(self) -> ureg.Quantity:
"""Return the abundance."""
return self._abundance
@property
def standard_abundance(self) -> ureg.Quantity:
"""Return the standard abundance in this phase."""
return PHASE_INFO_DICT[self._phase].standard_abundance
@property
def physiolical_abundance(self) -> ureg.Quantity:
"""Return the default physiological abundance in this phase."""
return PHASE_INFO_DICT[self._phase].physiolical_abundance
@property
def dimensionality(self) -> str:
"""Return the dimensionality of the abundance in this phase.
E.g. [concentration] for aqueous phase, or [pressure] for gas phase.
:return: the dimensionality in this phase, or None if abundance is
fixed.
"""
return PHASE_INFO_DICT[self._phase].dimensionality
@staticmethod
......@@ -172,10 +188,16 @@ class Condition(object):
self._abundance = abundance
def reset_abundance(self) -> None:
"""Reset the abundance to standard abundance."""
self._abundance = self.standard_abundance
@property
def is_physiological(self) -> bool:
"""Return True iff the abundance is the same as the physiological.
:return: True if the abundance is in physiological conditions,
or if the abundance if fixed in this phase anyway.
"""
if self.standard_abundance is None:
return True # when the phase does not allow relative abundances
if self.physiolical_abundance is None:
......@@ -185,17 +207,21 @@ class Condition(object):
class PhasedCompound(object):
"""A class that combines a equilibrator_api Compound and a Condition."""
def __init__(self, compound: Compound, condition: Condition = None):
"""Create a new PhasedCompound object."""
self.compound = compound
self.condition = condition or Condition.get_default(compound)
@property
def mnx_id(self):
"""Get the compound's MetaNetX ID."""
return self.compound.mnx_id
@property
def phase(self):
"""Get the phase."""
return self.condition.phase
@phase.setter
......@@ -220,6 +246,7 @@ class PhasedCompound(object):
@property
def abundance(self) -> ureg.Quantity:
"""Get the abundance."""
return self.condition.abundance
@abundance.setter
......@@ -238,6 +265,7 @@ class PhasedCompound(object):
@property
def ln_abundance(self) -> float:
"""Return the log of the abundance (for thermodynamic calculations)."""
if self.compound == Reaction.PROTON_COMPOUND:
# Since pH is an environmental parameter, we do not use the
# concentration of protons for energy calculations
......@@ -246,6 +274,7 @@ class PhasedCompound(object):
@property
def ln_physiological_abundance(self) -> float:
"""Return the log of the default physiological abundance."""
if self.compound == Reaction.PROTON_COMPOUND:
# Since pH is an environmental parameter, we do not use the
# concentration of protons for energy calculations
......@@ -254,6 +283,7 @@ class PhasedCompound(object):
@property
def is_physiological(self) -> bool:
"""Check if the abundance is physiological."""
return self.condition.is_physiological
@ureg.check(None, None, "[concentration]", "[temperature]")
......
......@@ -27,13 +27,13 @@
import logging
from typing import Dict, Tuple, Iterable, KeysView
from typing import Dict, Tuple
import numpy as np
from equilibrator_cache.reaction import Reaction
from . import Q_, Compound, ccache, ureg
from .phased_compound import PhasedCompound, Condition
from .phased_compound import PhasedCompound
class PhasedReaction(Reaction):
......@@ -64,21 +64,25 @@ class PhasedReaction(Reaction):
PhasedReaction.REACTION_COUNTER += 1
def clone(self):
"""Clone this reaction object."""
phased_reaction = PhasedReaction(self.sparse, self.arrow, self.rid)
phased_reaction.sparse_with_phases = dict(
self.sparse_with_phases.items())
return phased_reaction
def set_abundance(self, compound: Compound, abundance: ureg.Quantity):
"""Set the abundance of the compound."""
for phased_compound in self.sparse_with_phases.keys():
if phased_compound.compound == compound:
phased_compound.abundance = abundance
def reset_abundances(self):
"""Reset the abundance to standard levels."""
for phased_compound in self.sparse_with_phases.keys():
phased_compound.reset_abundance()
def set_phase(self, compound: Compound, phase: str):
"""Set the phase of the compound."""
for phased_compound in self.sparse_with_phases.keys():
if phased_compound.compound == compound:
phased_compound.phase = phase
......@@ -101,6 +105,10 @@ class PhasedReaction(Reaction):
def add_stoichiometry(self,
cpd: Compound,
coeff: float) -> None:
"""Add to the stoichiometric coefficient of a compound.
If this compound is not already in the reaction, add it.
"""
super(PhasedReaction, self).add_stoichiometry(cpd, coeff)
for phased_compound in self.sparse_with_phases.keys():
......
......@@ -49,6 +49,7 @@ def atp_hydrolysis() -> Reaction:
formula = "KEGG:C00002 + KEGG:C00001 = KEGG:C00008 + KEGG:C00009"
return Reaction.parse_formula(formula)
@pytest.fixture(scope="module")
def missing_h2o() -> Reaction:
"""Create a ATP hydrolysis reaction."""
......@@ -66,6 +67,7 @@ def fermentation_gas() -> Reaction:
def test_water_balancing(comp_contribution, missing_h2o):
"""Test if the reaction can be balanced using H2O."""
assert not missing_h2o.is_balanced()
assert missing_h2o.is_balanced(ignore_atoms=("H", "O", "e-"))
......@@ -75,6 +77,7 @@ def test_water_balancing(comp_contribution, missing_h2o):
)
assert balanced_rxn is not None
def test_atp_hydrolysis_physiological_dg(comp_contribution, atp_hydrolysis):
"""Test the dG adjustments for physiological conditions (with H2O)."""
warnings.simplefilter('ignore', ResourceWarning)
......@@ -145,6 +148,7 @@ def test_reduction_potential(comp_contribution):
reaction = Reaction.parse_formula(formula)
assert reaction.check_half_reaction_balancing() == 2
assert reaction.is_balanced(ignore_atoms=("H", "e-"))
standard_e_prime, e_uncertainty = comp_contribution.standard_e_prime(
reaction)
......@@ -162,14 +166,3 @@ def test_unresolved_reactions(comp_contribution):
_, dg_uncertainty = comp_contribution.standard_dg_prime(reaction)
assert float(dg_uncertainty / Q_("kJ/mol")) > 1e4
def test_reduction_potential(comp_contribution):
"""Test the CC predictions for a redox half-reaction."""
warnings.simplefilter('ignore', ResourceWarning)
# oxaloacetate = malate
formula = "KEGG:C00036 = KEGG:C00149"
reaction = Reaction.parse_formula(formula)
assert reaction.is_balanced(ignore_atoms=("H", "e-"))
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment