In [1]:
%matplotlib inline
import math
from ecell4 import *
from ecell4_base import *
from ecell4_base.core import *
In [2]:
def create_simulator(f=gillespie.Factory()):
m = NetworkModel()
A, B, C = Species('A', 0.005, 1), Species('B', 0.005, 1), Species('C', 0.005, 1)
m.add_species_attribute(A)
m.add_species_attribute(B)
m.add_species_attribute(C)
m.add_reaction_rule(create_binding_reaction_rule(A, B, C, 0.01))
m.add_reaction_rule(create_unbinding_reaction_rule(C, A, B, 0.3))
w = f.world()
w.bind_to(m)
w.add_molecules(C, 60)
sim = f.simulator(w)
sim.initialize()
return sim
最も一般的な Observer
の1つはFixedIntervalNumberObserver
です。これは与えられた時間間隔で分子の数を記録します。 FixedIntervalNumberObserver
は、時間間隔と、ログの対象とするのSpecies
のシリアルのリストを必要とします。
In [3]:
obs1 = FixedIntervalNumberObserver(0.1, ['A', 'B', 'C'])
sim = create_simulator()
sim.run(1.0, obs1)
FixedIntervalNumberObserver
のdata
関数はログに記録されたデータを返します。
In [4]:
print(obs1.data())
targets()
はコンストラクタの引数として指定した Species
のリストを返します。
In [5]:
print([sp.serial() for sp in obs1.targets()])
NumberObserver
は、反応が起こったときのすべてのステップの後に分子の数を記録します。
このオブザーバーはすべての反応を記録するのに便利ですが、 ode
では利用できません。
In [6]:
obs1 = NumberObserver(['A', 'B', 'C'])
sim = create_simulator()
sim.run(1.0, obs1)
print(obs1.data())
TimingNumberObserver
では、ログの時刻をそのコンストラクタの引数として与えることができます。
In [7]:
obs1 = TimingNumberObserver([0.0, 0.1, 0.2, 0.5, 1.0], ['A', 'B', 'C'])
sim = create_simulator()
sim.run(1.0, obs1)
print(obs1.data())
run
関数は複数のオブザーバを一度に受け付けます。
In [8]:
obs1 = NumberObserver(['C'])
obs2 = FixedIntervalNumberObserver(0.1, ['A', 'B'])
sim = create_simulator()
sim.run(1.0, [obs1, obs2])
print(obs1.data())
print(obs2.data())
FixedIntervalHDF5Observedr
はWorld
のデータ全体を一定の間隔で出力ファイルに記録します。
2番目の引数は、出力ファイル名の接頭辞です。
filename()
は、次に保存するようにスケジュールされたファイルの名前を返します。
%02d
のような多くのフォーマット文字列では、ファイル名にステップカウントを使用することができます。
書式文字列を使用しないと、最新のデータがファイルに上書きされます。
In [9]:
obs1 = FixedIntervalHDF5Observer(0.2, 'test%02d.h5')
print(obs1.filename())
sim = create_simulator()
sim.run(1.0, obs1)
print(obs1.filename())
In [10]:
w = load_world('test05.h5')
print(w.t(), w.num_molecules(Species('C')))
FixedIntervalCSVObserver
の使用方法は、FixedIntervalHDF5Observer
の使用方法とほぼ同じです。
FixedIntervalCSVObserver
は半径(r)とSpecies
のシリアル番号(sid)を持つパーティクルの位置(x、y、z)をCSVファイルに保存します。
In [11]:
obs1 = FixedIntervalCSVObserver(0.2, "test%02d.csv")
print(obs1.filename())
sim = create_simulator()
sim.run(1.0, obs1)
print(obs1.filename())
下記は出力CSVファイルの最初の10行です。
In [12]:
print(''.join(open("test05.csv").readlines()[: 10]))
粒子シミュレーションのために、E-Cell4は、分子の軌道を追跡するためのオブザーバ(Observer)を提供し、これはFixedIntervalTrajectoryObserver
と名付けられています。
ParticleID
が特に指定されていないときは、すべての軌跡を記録します。
シミュレーション中にパーティクルIDが反応のために失われると、FixedIntervalTrajectoryObserver
はパーティクルをそれ以上トレースするのを単に止めます。
In [13]:
sim = create_simulator(spatiocyte.Factory(0.005))
obs1 = FixedIntervalTrajectoryObserver(0.01)
sim.run(0.1, obs1)
In [14]:
print([tuple(pos) for pos in obs1.data()[0]])
ほとんどの場合、World
は各平面の周期的境界を想定しています。
境界条件に起因するエッジでのパーティクルの大きなジャンプを避けるために、 FixedIntervalTrajectoryObserver
は位置のシフトを維持しようとします。
従って、Observer
に格納されたパーティクルの位置は、World
に対して与えられた立方体に必ずしも限定されません。
境界条件の拡散を正確に追跡するには、ロギングのステップ間隔を十分小さくする必要があります。
もちろん、このオプションは無効にすることができます。
help(FixedIntervalTrajectoryObserver)
を参照してください。
In [15]:
obs1 = NumberObserver(['C'])
obs2 = FixedIntervalNumberObserver(0.1, ['A', 'B'])
sim = create_simulator()
sim.run(10.0, [obs1, obs2])
In [16]:
viz.plot_number_observer(obs1, obs2)
プロットのスタイルを設定したり、プロットに任意の関数を追加することもできます。
In [17]:
viz.plot_number_observer(obs1, '-', obs2, ':', lambda t: 60 * (1 + 2 * math.exp(-0.9 * t)) / (2 + math.exp(-0.9 * t)), '--')
位相平面でのプロットは、x軸とy軸を指定することによっても利用できます。
In [18]:
viz.plot_number_observer(obs2, 'o', x='A', y='B')
空間シミュレーションでは、World
の状態を可視化するために、viz.plot_world
が利用可能です。
この関数は、インタラクティブな方法で3次元ボリューム内のパーティクルの点をプロットします。
描画領域の右ボタンをクリックすると、画像を保存できます。
In [19]:
sim = create_simulator(spatiocyte.Factory(0.005))
# viz.plot_world(sim.world())
viz.plot_world(sim.world(), interactive=False)
FixedIntervalHDF5Observer
として与えられた一連のHDF5ファイルからムービーを作ることもできます。
注: viz.plot_movie
は、オプションinteractive=False
の時に追加ライブラリ ffmpeg
を必要とします。
In [20]:
sim = create_simulator(spatiocyte.Factory(0.005))
obs1 = FixedIntervalHDF5Observer(0.02, 'test%02d.h5')
sim.run(1.0, obs1)
viz.plot_movie(obs1)
最後に、 FixedIntervalTrajectoryObserver
に対応して、viz.plot_trajectory
はパーティクル軌道の可視化を提供します。
In [21]:
sim = create_simulator(spatiocyte.Factory(0.005))
obs1 = FixedIntervalTrajectoryObserver(1e-3)
sim.run(1, obs1)
# viz.plot_trajectory(obs1)
viz.plot_trajectory(obs1, interactive=False)