A up-regulates B ,¶A + X <-> 2B (mostly forward), where X is plentiful¶1st-order kinetics.
If [A] is low, [B] remains low, too. Then, if [A] goes high, then so does [B]. However, at that point, A can no longer bring B down to any substantial extent.
See also the experiment "1D/reactions/up_regulation_1"
LAST REVISED: June 23, 2024 (using v. 1.0 beta36)
import set_path # Importing this module will add the project's home directory to sys.path
Added 'D:\Docs\- MY CODE\BioSimulations\life123-Win7' to sys.path
from experiments.get_notebook_info import get_notebook_basename
from life123 import ChemData as chem
from life123 import UniformCompartment
from life123 import GraphicLog
# Initialize the HTML logging
log_file = get_notebook_basename() + ".log.htm" # Use the notebook base filename for the log file
# Set up the use of some specified graphic (Vue) components
GraphicLog.config(filename=log_file,
components=["vue_cytoscape_2"],
extra_js="https://cdnjs.cloudflare.com/ajax/libs/cytoscape/3.21.2/cytoscape.umd.js")
-> Output will be LOGGED into the file 'up_regulate_1.log.htm'
# Initialize the system
chem_data = chem(names=["A", "X", "B"])
# Reaction A + X <-> 2B , with 1st-order kinetics for all species
chem_data.add_reaction(reactants=["A" , "X"], products=[(2, "B", 1)],
forward_rate=8., reverse_rate=2.)
chem_data.describe_reactions()
# Send the plot of the reaction network to the HTML log file
chem_data.plot_reaction_network("vue_cytoscape_2")
Number of reactions: 1 (at temp. 25 C)
0: A + X <-> 2 B (kF = 8 / kR = 2 / delta_G = -3,436.6 / K = 4) | 1st order in all reactants & products
Set of chemicals involved in the above reactions: {'A', 'X', 'B'}
[GRAPHIC ELEMENT SENT TO LOG FILE `up_regulate_1.log.htm`]
dynamics = UniformCompartment(chem_data=chem_data, preset="fast")
dynamics.set_conc(conc={"A": 5., "X": 100.},
snapshot=True) # A is scarce, X is plentiful, B is absent
dynamics.describe_state()
SYSTEM STATE at Time t = 0:
3 species:
Species 0 (A). Conc: 5.0
Species 1 (X). Conc: 100.0
Species 2 (B). Conc: 0.0
Set of chemicals involved in reactions: {'A', 'X', 'B'}
dynamics.set_diagnostics() # To save diagnostic information about the call to single_compartment_react()
dynamics.single_compartment_react(initial_step=0.0005, duration=0.015,
variable_steps=True)
27 total step(s) taken
Number of step re-do's because of negative concentrations: 0
Number of step re-do's because of elective soft aborts: 1
Norm usage: {'norm_A': 8, 'norm_B': 7, 'norm_C': 7, 'norm_D': 7}
dynamics.plot_history(colors=['red', 'darkorange', 'green'], show_intervals=True)
A, as the scarse limiting reagent, stops the reaction.
As long as A is low, B also remains low.
dynamics.get_history()
| SYSTEM TIME | A | X | B | caption | |
|---|---|---|---|---|---|
| 0 | 0.000000 | 5.000000 | 100.000000 | 0.000000 | Initialized state |
| 1 | 0.000300 | 3.800000 | 98.800000 | 2.400000 | |
| 2 | 0.000600 | 2.900384 | 97.900384 | 4.199232 | |
| 3 | 0.000900 | 2.221427 | 97.221427 | 5.557147 | |
| 4 | 0.001200 | 1.706432 | 96.706432 | 6.587135 | |
| 5 | 0.001500 | 1.314329 | 96.314329 | 7.371341 | |
| 6 | 0.001800 | 1.014939 | 96.014939 | 7.970122 | |
| 7 | 0.002100 | 0.785843 | 95.785843 | 8.428314 | |
| 8 | 0.002400 | 0.610246 | 95.610246 | 8.779509 | |
| 9 | 0.002700 | 0.475484 | 95.475484 | 9.049033 | |
| 10 | 0.003000 | 0.371960 | 95.371960 | 9.256080 | |
| 11 | 0.003300 | 0.292375 | 95.292375 | 9.415250 | |
| 12 | 0.003600 | 0.231157 | 95.231157 | 9.537685 | |
| 13 | 0.003900 | 0.184048 | 95.184048 | 9.631904 | |
| 14 | 0.004200 | 0.147783 | 95.147783 | 9.704434 | |
| 15 | 0.004500 | 0.119859 | 95.119859 | 9.760283 | |
| 16 | 0.004800 | 0.098352 | 95.098352 | 9.803295 | |
| 17 | 0.005100 | 0.081787 | 95.081787 | 9.836426 | |
| 18 | 0.005400 | 0.069025 | 95.069025 | 9.861949 | |
| 19 | 0.005700 | 0.059193 | 95.059193 | 9.881614 | |
| 20 | 0.006150 | 0.047830 | 95.047830 | 9.904340 | |
| 21 | 0.006600 | 0.040378 | 95.040378 | 9.919244 | |
| 22 | 0.007050 | 0.035490 | 95.035490 | 9.929020 | |
| 23 | 0.007725 | 0.030681 | 95.030681 | 9.938638 | |
| 24 | 0.008737 | 0.027190 | 95.027190 | 9.945620 | |
| 25 | 0.010256 | 0.026007 | 95.026007 | 9.947986 | |
| 26 | 0.012534 | 0.026292 | 95.026292 | 9.947415 | |
| 27 | 0.015952 | 0.025975 | 95.025975 | 9.948051 |
dynamics.explain_time_advance()
From time 0 to 0.0057, in 19 steps of 0.0003 From time 0.0057 to 0.00705, in 3 steps of 0.00045 From time 0.00705 to 0.007725, in 1 step of 0.000675 From time 0.007725 to 0.008737, in 1 step of 0.00101 From time 0.008737 to 0.01026, in 1 step of 0.00152 From time 0.01026 to 0.01253, in 1 step of 0.00228 From time 0.01253 to 0.01595, in 1 step of 0.00342 (27 steps total)
# Verify that the reaction has reached equilibrium
dynamics.is_in_equilibrium()
0: A + X <-> 2 B
Final concentrations: [A] = 0.02597 ; [X] = 95.03 ; [B] = 9.948
1. Ratio of reactant/product concentrations, adjusted for reaction orders: 4.03037
Formula used: [B] / ([A][X])
2. Ratio of forward/reverse reaction rates: 4
Discrepancy between the two values: 0.7592 %
Reaction IS in equilibrium (within 1% tolerance)
True
dynamics.set_single_conc(species_name="A", conc=50., snapshot=True)
dynamics.describe_state()
SYSTEM STATE at Time t = 0.015951562:
3 species:
Species 0 (A). Conc: 50.0
Species 1 (X). Conc: 95.02597471866889
Species 2 (B). Conc: 9.948050562662225
Set of chemicals involved in reactions: {'A', 'X', 'B'}
dynamics.get_history(tail=5)
| SYSTEM TIME | A | X | B | caption | |
|---|---|---|---|---|---|
| 24 | 0.008737 | 0.027190 | 95.027190 | 9.945620 | |
| 25 | 0.010256 | 0.026007 | 95.026007 | 9.947986 | |
| 26 | 0.012534 | 0.026292 | 95.026292 | 9.947415 | |
| 27 | 0.015952 | 0.025975 | 95.025975 | 9.948051 | |
| 28 | 0.015952 | 50.000000 | 95.025975 | 9.948051 | Set concentration of `A` |
Notice the discontity in [A] in the last 2 rows
dynamics.single_compartment_react(initial_step=0.0005, target_end_time=0.035,
variable_steps=True)
Some steps were backtracked and re-done, to prevent negative concentrations or excessively large concentration changes
51 total step(s) taken
Number of step re-do's because of negative concentrations: 0
Number of step re-do's because of elective soft aborts: 5
Norm usage: {'norm_A': 35, 'norm_B': 19, 'norm_C': 19, 'norm_D': 19}
dynamics.plot_history(colors=['red', 'darkorange', 'green'], show_intervals=True)
A, still the limiting reagent, is again eventually stopping the reaction...
The (transiently) high value of [A] led to a high value of [B]
Notice how the variable time steps automatically adapt.
#dynamics.get_history()
#dynamics.explain_time_advance()
# Verify that the reaction has reached equilibrium
dynamics.is_in_equilibrium()
0: A + X <-> 2 B
Final concentrations: [A] = 0.5992 ; [X] = 45.63 ; [B] = 108.7
1. Ratio of reactant/product concentrations, adjusted for reaction orders: 3.97761
Formula used: [B] / ([A][X])
2. Ratio of forward/reverse reaction rates: 4
Discrepancy between the two values: 0.5598 %
Reaction IS in equilibrium (within 1% tolerance)
True
dynamics.set_single_conc(species_name="A", conc=30., snapshot=True)
dynamics.describe_state()
SYSTEM STATE at Time t = 0.039055056:
3 species:
Species 0 (A). Conc: 30.0
Species 1 (X). Conc: 45.62521424281943
Species 2 (B). Conc: 108.74957151436116
Set of chemicals involved in reactions: {'A', 'X', 'B'}
dynamics.get_history(tail=5)
| SYSTEM TIME | A | X | B | caption | |
|---|---|---|---|---|---|
| 76 | 0.028635 | 0.690343 | 45.716318 | 108.567364 | |
| 77 | 0.030829 | 0.612807 | 45.638782 | 108.722436 | |
| 78 | 0.034119 | 0.592086 | 45.618060 | 108.763879 | |
| 79 | 0.039055 | 0.599240 | 45.625214 | 108.749572 | |
| 80 | 0.039055 | 30.000000 | 45.625214 | 108.749572 | Set concentration of `A` |
dynamics.single_compartment_react(initial_step=0.0005, target_end_time=0.070,
variable_steps=True)
28 total step(s) taken
Number of step re-do's because of negative concentrations: 0
Number of step re-do's because of elective soft aborts: 3
Norm usage: {'norm_A': 22, 'norm_B': 14, 'norm_C': 14, 'norm_D': 14}
dynamics.plot_history(colors=['red', 'darkorange', 'green'], show_intervals=True)
A, again the scarce limiting reagent, stops the reaction yet again.
And, again, the (transiently) high value of [A] up-regulated [B]
Notes:
A can up-regulate B, but it cannot bring it down.
X will soon need to be replenished, if A is to continue being the limiting reagent.**
# Zoom in on the early part of the last plot
dynamics.plot_history(colors=['red', 'darkorange', 'green'], xrange=[0, 0.02])
# Look up the first intersection of the [A] and [B] curves
dynamics.curve_intersect("A", "B", t_start=0, t_end=0.01)
(0.00045562195425603814, 3.333333333333333)
# The next intersection isn't particulary meaning; just an artifact of the sudden jump in [A]
dynamics.curve_intersect("A", "B", t_start=0.01, t_end=0.02)
WARNING: curve_intersect(): Discontinuity detected at `SYSTEM TIME` = 0.015951562499999995
(0.015951562499999995, 9.948050562662225)
# The final intersection
dynamics.curve_intersect("A", "B", t_start=0.016, t_end=0.02)
(0.01638486713665179, 36.649350187554084)
# Verify that the reaction has reached equilibrium
dynamics.is_in_equilibrium()
0: A + X <-> 2 B
Final concentrations: [A] = 2.284 ; [X] = 17.91 ; [B] = 164.2
1. Ratio of reactant/product concentrations, adjusted for reaction orders: 4.01395
Formula used: [B] / ([A][X])
2. Ratio of forward/reverse reaction rates: 4
Discrepancy between the two values: 0.3487 %
Reaction IS in equilibrium (within 1% tolerance)
True