Python · chapter 9 of 13

Exporting data and reproducing it

grn.export

files = grn.export(data, filename) writes a Solution or a Screen. The format follows the extension.

.npz

A NumPy archive with the arrays (t, x, x_clean when present, ic, S, labels, state_labels; for screens X, rows, converged) plus the whole object pickled under the key data. Load the arrays with np.load(f); recover the object with pickle.loads(np.load(f)["data"].tobytes()).

.pkl

The object itself, pickled. Models rebuild their callables on load. A stimulus with a custom function given as a lambda cannot be pickled; use a module-level function instead.

.csv

Three files are written and their names returned:

FileContents
<name>.csvThe data as a table
<name>_truth.csvEdge list with columns source, target, sign (labels, and +1/-1)
<name>_adjacency.csvThe signed n x n matrix S, one header row of gene labels

The data table layout:

DataColumns
Time series, one cellt, then one column per state (sol.state_labels)
Time series, several cellscell (1-based), t, then the states; rows are ordered time within cell
Screenperturbation (wildtype or the perturbed gene), then the states

For two-stage models the state columns are <gene>_mRNA and <gene>_protein. The CSV layout is identical to the MATLAB toolbox's, so datasets can be exchanged between the two.

files = grn.export(sol, "run1.csv")
import pandas as pd                                  # optional
tbl = pd.read_csv(files[0]); edges = pd.read_csv(files[1])
S = np.loadtxt(files[2], delimiter=",", skiprows=1)

For a three-gene, two-cell time series:

Output
abc.csv
abc_truth.csv
abc_adjacency.csv

--- abc.csv (first lines)
cell,t,A,B,C
1,0.0,0.5972686479665021,1.4905748750803098,0.3522700566259267
1,0.1,0.6912066583716652,1.7360762199059365,0.7394624897991464
1,0.2,0.7749416139930516,1.9844917781853426,1.1003512363313355
1,0.30000000000000004,0.8494134216225173,2.2308859505158045,1.434597095465921

--- abc_truth.csv (first lines)
source,target,sign
A,B,1
B,C,-1
C,A,-1

--- abc_adjacency.csv (first lines)
A,B,C
0,0,-1
1,0,0
0,-1,0

A complete recipe

Because every option is recorded, the following regenerates a dataset exactly:

import pickle
data = pickle.load(open("run1.pkl", "rb"))
o = data.options
sol = grn.simulate(data.model, duration=o["duration"], sample_dt=o["sample_dt"],
                   transient=o["transient"], cells=o["cells"], random_ic=o["random_ic"],
                   initial_condition=data.ic, noise=o["noise"], noise_strength=o["noise_strength"],
                   dt=o["dt"], noise_sigma=o["noise_sigma"], seed=o["seed"], stimulus=data.stimulus)
np.array_equal(sol.x, data.x)      # True

Passing initial_condition=data.ic (the (dim, cells) initial conditions actually used) reproduces random initial conditions without redrawing them; leaving it out and keeping random_ic and seed gives the same result too.

What to ship with a benchmark