Hi all,

To aid in working out what features we should include in CellML 1.2, I 
have been looking into one of the major difficulties with creating 
re-usable metabolic models at the moment: that to compute a derivative, 
you need to know all the fluxes, but when a model is extended, new 
fluxes can be added to the model. Ideally, we should be able to define 
CellML 1.2 so that structured types can be leveraged to avoid this issue.

I have come up with an example of how this might look in CellML 1.2. 
This is based in part off a discussion that I had earlier with Poul, so 
most of the credit for this goes to him, while most of the blame for the 
inelegant parts goes to me.

Note that the lambda constructs without any bound variables are there to 
defer interpretation of the fluxes until they are taken from the set. 
The rationale for needing this is that if we had two statements that a 
certain real-valued flux belongs in the set, and two of them happened to 
have the same value at a particular point in time, then summing over the 
set would only include the flux value once (e.g. saying x is an element 
of N, where N is in the natural numbers, means that the value of x is a 
natural number. Saying x=5, y=5, x in N, y in N does not mean that 5 is 
in the set of natural numbers twice). On the other hand, we can have two 
different zero argument lambda functions in a set, which just happen to 
evaluate to the same value. This is consistent with the declarative 
nature of CellML - we are not saying 'add this flux to the set of 
fluxes', but rather, we are making a series of statements about what is 
in the set of fluxes, and the processing software is then summing over 
all fluxes which have been explicitly mentioned. Because we can connect 
the set of fluxes up to an importing model, doing things this way gives 
a great deal of extra flexibility.

Notes:
1) In practice, the substance could become an import which is re-used 
many times, and likewise for components representing various general 
types of chemical reactions.
2) I have invented a possible way in which we could remove 
directionality from connections. No one has come up with a formal 
proposal to do it this way yet.
3) I have followed Randall's earlier suggestion about how to structure 
connections without using component_ref. This again needs a formal 
proposal and discussion.
4) The model uses a potential way in which we could get rid of the 
generality of groups, by replacing group and relationship_ref with a 
simple encapsulation element. This again needs to be formally proposed 
and discussed at some point.

<?xml version="1.0" encoding="UTF-8"?>
<model
  xmlns="http://www.cellml.org/cellml/1.1#";
  xmlns:c11="http://www.cellml.org/cellml/1.1#";
  xmlns:c12="http://www.cellml.org/cellml/1.2#";
  xmlns:m="http://www.w3.org/1998/Math/MathML";
  name="_1_2_example"
 >
  <component name="substance_x">
    <c12:variable name="fluxes" type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" public_interface="yes" />
    <c12:variable name="concentration" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="time" units="second" public_interface="yes" />
    <m:math>
      <m:apply><m:eq/>
        <m:apply><m:diff/>
          <m:bvar><m:ci>time</m:ci></m:bvar>
          <m:ci>concentration</m:ci>
        </m:apply>
        <m:apply><m:sum />
          <m:bvar><m:ci>f</m:ci></m:bvar>
          <m:condition>
            <m:apply>
              <m:in/>
              <m:ci>f</m:ci>
              <m:ci>fluxes</m:ci>
            </m:apply>
          </m:condition>
          <m:apply>
            <m:ci>f</m:ci>
          </m:apply>
        </m:apply>
      </m:apply>
    </m:math>
  </component>

  <component name="substance_a">
    <!-- Identical to substance_x. This would normally be defined once 
and imported.
      -->
  </component>

  <component name="substance_b">
    <!-- Identical to substance_x. This would normally be defined once 
and imported.
      -->
  </component>

  <component name="substance_y">
    <!-- Identical to substance_x. This would normally be defined once 
and imported.
      -->
  </component>

  <!-- Represents a reaction A + B -> X -->
  <component name="reaction_a_b_x">
    <c12:variable name="concentration_a" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_b" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_x" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="flux_a"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_b"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_x"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <variable name="kf" units="litres_per_mol_per_second" 
initial_value="0.5" />
    <variable name="kb" units="litres_per_mol_per_second" 
initial_value="0.1" />
    <variable name="overall_rate" units="mol_per_litre_per_second" />
    <m:math>
      <m:apply><m:eq/>
        <m:ci>overall_rate</m:ci>
        <!-- First order law of mass action... -->
        <m:apply><m:minus/>
          <m:apply><m:times/>
            <m:ci>kf</m:ci>
            <m:ci>concentration_a</m:ci>
            <m:ci>concentration_b</m:ci>
          </m:apply>
          <m:apply><m:times/>
            <m:ci>kb</m:ci>
            <m:ci>concentration_x</m:ci>
          </m:apply>
        </m:apply>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:apply><m:minus/>
            <m:ci>overall_rate</m:ci>
          </m:apply>
        </m:lambda>
        <m:ci>flux_a</m:ci>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:apply><m:minus/>
            <m:ci>overall_rate</m:ci>
          </m:apply>
        </m:lambda>
        <m:ci>flux_b</m:ci>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:ci>overall_rate</m:ci>
        </m:lambda>
        <m:ci>flux_x</m:ci>
      </m:apply>
    </m:math>
  </component>

  <!-- Represents a reaction A + X -> Y -->
  <component name="reaction_a_x_y">
    <c12:variable name="concentration_a" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_y" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_x" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="flux_a"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_y"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_x"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <variable name="kf" units="litres_per_mol_per_second" 
initial_value="0.5" />
    <variable name="kb" units="litres_per_mol_per_second" 
initial_value="0.1" />
    <variable name="overall_rate" units="mol_per_litre_per_second" />
    <m:math>
      <m:apply><m:eq/>
        <m:ci>overall_rate</m:ci>
        <!-- First order law of mass action... -->
        <m:apply><m:minus/>
          <m:apply><m:times/>
            <m:ci>kf</m:ci>
            <m:ci>concentration_a</m:ci>
            <m:ci>concentration_x</m:ci>
          </m:apply>
          <m:apply><m:times/>
            <m:ci>kb</m:ci>
            <m:ci>concentration_y</m:ci>
          </m:apply>
        </m:apply>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:apply><m:minus/>
            <m:ci>overall_rate</m:ci>
          </m:apply>
        </m:lambda>
        <m:ci>flux_a</m:ci>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:apply><m:minus/>
            <m:ci>overall_rate</m:ci>
          </m:apply>
        </m:lambda>
        <m:ci>flux_x</m:ci>
      </m:apply>
      <m:apply><m:in/>
        <m:lambda>
          <m:ci>overall_rate</m:ci>
        </m:lambda>
        <m:ci>flux_y</m:ci>
      </m:apply>
    </m:math>
  </component>

  <component name="abxy_system">
    <c12:variable name="concentration_a" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_b" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_x" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="concentration_y" units="mol_per_litre"
                  public_interface="yes" />
    <c12:variable name="flux_a"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_b"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_x"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
    <c12:variable name="flux_y"
                  public_interface="yes"
                  type="set_of_lambda_of_real"
                  units="mol_per_litre_per_second" />
  </component>

  <c12:connection component_1="substance_a" component_2="reaction_a_b_x">
    <variable_ref variable_1="concentration" variable_2="concentration_a" />
    <variable_ref variable_1="flux" variable_2="flux_a" />
  </c12:connection>
  <c12:connection component_1="substance_b" component_2="reaction_a_b_x">
    <variable_ref variable_1="concentration" variable_2="concentration_b" />
    <variable_ref variable_1="flux" variable_2="flux_b" />
  </c12:connection>
  <c12:connection component_1="substance_x" component_2="reaction_a_b_x">
    <variable_ref variable_1="concentration" variable_2="concentration_x" />
    <variable_ref variable_1="flux" variable_2="flux_x" />
  </c12:connection>

  <c12:connection component_1="substance_a" component_2="reaction_a_x_y">
    <variable_ref variable_1="concentration" variable_2="concentration_a" />
    <variable_ref variable_1="flux" variable_2="flux_a" />
  </c12:connection>
  <c12:connection component_1="substance_x" component_2="reaction_a_x_y">
    <variable_ref variable_1="concentration" variable_2="concentration_x" />
    <variable_ref variable_1="flux" variable_2="flux_x" />
  </c12:connection>
  <c12:connection component_1="substance_y" component_2="reaction_a_x_y">
    <variable_ref variable_1="concentration" variable_2="concentration_y" />
    <variable_ref variable_1="flux" variable_2="flux_y" />
  </c12:connection>

  <c12:connection component_1="substance_a" component_2="abxy_system">
    <variable_ref variable_1="concentration" variable_2="concentration_a" />
    <variable_ref variable_1="flux" variable_2="flux_a" />
  </c12:connection>
  <c12:connection component_1="substance_b" component_2="abxy_system">
    <variable_ref variable_1="concentration" variable_2="concentration_b" />
    <variable_ref variable_1="flux" variable_2="flux_b" />
  </c12:connection>
  <c12:connection component_1="substance_x" component_2="abxy_system">
    <variable_ref variable_1="concentration" variable_2="concentration_x" />
    <variable_ref variable_1="flux" variable_2="flux_x" />
  </c12:connection>
  <c12:connection component_1="substance_y" component_2="abxy_system">
    <variable_ref variable_1="concentration" variable_2="concentration_y" />
    <variable_ref variable_1="flux" variable_2="flux_y" />
  </c12:connection>

  <c12:encapsulation>
    <component_ref component="abxy_system">
      <component_ref component="substance_a"/>
      <component_ref component="substance_b"/>
      <component_ref component="substance_x"/>
      <component_ref component="substance_y"/>
      <component_ref component="reaction_a_b_x"/>
      <component_ref component="reaction_a_x_y"/>
    </component_ref>
  </c12:encapsulation>

  <!-- Units would also be defined here, as in CellML 1.1... -->
</model>

_______________________________________________
cellml-discussion mailing list
cellml-discussion@cellml.org
http://www.cellml.org/mailman/listinfo/cellml-discussion

Reply via email to