|
|
"""
Dose-dependency of pharmacokinetic parameters.
"""
from typing import Dict
import pandas as pd
import numpy as np
from sbmlsim.experiment import ExperimentDict
from sbmlsim.data import DataSet, Data
from sbmlsim.result import XResult
from sbmlsim.result.datagenerator import DataGenerator
from sbmlsim.simulation import Timecourse, TimecourseSim, ScanSim, Dimension
from sbmlsim.plot.plotting_matplotlib import Figure, Axis
from . import MidazolamSimulationExperiment
class PKScanExperiment(MidazolamSimulationExperiment):
def simulations(self) -> Dict[str, ScanSim]:
""" Scanning dose-response of midazolam pharmacokinetics."""
tend = 1000 # [min]
steps = 2000
Q_ = self.Q_
scan_defs = {
"po_scan": {'PODOSE_mid': Q_(np.logspace(-1, 1.61, num=20), 'mg')},
"iv_scan": {'IVDOSE_mid': Q_(np.logspace(-1, 1.17, num=20), 'mg')},
}
tcscans = ExperimentDict()
for key, changes in scan_defs.items():
tcscans[key] = ScanSim(simulation=
TimecourseSim([
Timecourse(start=0, end=tend, steps=steps,
changes={
**self.default_changes(),
})
]),
dimensions=[
Dimension("dim_dose", changes=changes),
Dimension("dim_bw", changes={
"BW": Q_(np.linspace(start=65, stop=100, num=10), "kg"),
})
]
)
return tcscans
def datagenerators(self) -> Dict[str, DataGenerator]:
self.add_selections(selections=[
"time", "[Cve_mid]", "[Cve_mid1oh]", "IVDOSE_mid", "PODOSE_mid"
])
"""
class DataGenerator1(DataGenerator):
def __call__(self, xresults: Dict[str, XResult], dsets=None) -> Dict[str, XResult]:
results = {}
for key, xres in xresults.items():
xres_new = XResult(xdataset=xres.xds.isel("_time", 0), udict=xres.udict, ureg=xres.ureg)
results[key] = xres_new
from matplotlib import pyplot as plt
# plt.plot(res_first['res1']["IVDOSE_mid"], res_last['res1']["Cve_mid"], 'o')
# plt.show()
x = (res_first['res1']["IVDOSE_mid"]).mean(dim="dim_bw")
y = (res_last['res1']['[Cve_mid]']).mean(dim="dim_bw")
ystd = (res_last['res1']['[Cve_mid]']).std(dim="dim_bw")
# add some custom data calculation
"""
def figures(self) -> Dict[str, Figure]:
return {
**self.fig_timecourse(),
**self.fig_dose(),
# **self.Fig3(),
}
def fig_timecourse(self) -> Dict[str, Figure]:
unit_time = "min"
unit_mid = "nmol/ml"
unit_mid1oh = "nmol/ml"
fig = Figure(self, sid="Fig1",
num_rows=2, num_cols=2, name=self.sid)
plots = fig.create_plots(
Axis("time", unit=unit_time),
legend=True
)
# set titles and labs
plots[0].set_title("scan po")
plots[1].set_title("scan iv")
for k in (0, 1):
plots[k].set_yaxis("midazolam", unit_mid)
plots[k].xaxis.label_visible = False
for k in (2, 3):
plots[k].set_yaxis("1-hydroxymidazolam", unit_mid1oh)
# simulation
for k, key in enumerate(["po_scan", "iv_scan"]):
task_id = f"task_{key}"
# plot midazolam
plots[k].add_data(task=task_id, xid='time', yid='[Cve_mid]',
color="black")
# plot 1-hydroxymidazolam
plots[k+2].add_data(task=task_id, xid='time', yid='[Cve_mid1oh]',
color="black")
return ExperimentDict({"fig1": fig})
def fig_dose(self) -> Dict[str, Figure]:
fig_id = "fig_dose"
unit_time = "min"
unit_mid = "nmol/ml"
unit_mid1oh = "nmol/ml"
unit_dose = "mg"
fig = Figure(self, sid=fig_id,
num_rows=1, num_cols=2, name=self.sid)
plots = fig.create_plots(
legend=True
)
# set titles and labs
plots[0].set_title("scan po")
plots[1].set_title("scan iv")
for k in (0, 1):
plots[k].set_xaxis("dose", unit_dose)
plots[k].set_yaxis("concentration", unit_mid)
# simulation
for k, sim_id in enumerate(["po_scan", "iv_scan"]):
task_id = f"task_{sim_id}"
xid = f"{sim_id.split('_')[0].upper()}DOSE_mid"
for sid in ["mid", "mid1oh"]:
plots[k].add_data(task=task_id, xid=xid, yid=f'[Cve_{sid}]',
color="black", linestyle="")
return ExperimentDict({fig_id: fig})
'''
def Fig3(self) -> Dict[str, Figure]:
Q_ = self.ureg.Quantity
unit_dose = "mg"
# calculate all pharmacokinetic parameters from scans
dfs = {}
for key in self._simulations.keys():
xres = self.results[f"task_{key}"]
if key.startswith("midpo"):
dose_vec = Q_(xres["PODOSE_mid"].values[0], xres.udict["PODOSE_mid"])
elif key.startswith("midiv"):
dose_vec = Q_(xres["IVDOSE_mid"].values[0], xres.udict["IVDOSE_mid"])
time_vec = xres.dim_mean('time')
pk_dicts = []
for k, dose in enumerate(dose_vec):
dose = dose.to("mol", "chemistry", mw=self.Mr.mid)
conc = Q_(xres["[Cve_mid]"].sel(dim_dose=k).values, xres.udict['[Cve_mid]'])
tcpk = TimecoursePK(
time=time_vec,
concentration=conc,
substance="midazolam",
dose=dose,
ureg=self.ureg
)
pk_dicts.append(tcpk.pk.to_dict())
df = pd.DataFrame(pk_dicts)
# Fix for unsorted rows
df = df.sort_values(by=["dose"])
dfs[key] = df
# TODO: calculate bioavailability from simulations (oral & iv simulation)
# visualize pharmacokinetic parameters
figures = {}
for pkkey in ["auc", "aucinf", "tmax", "cmax", "kel", "thalf", "vd", "vdss", "cl"]:
print("-" * 80)
print(f"{pkkey}")
print("-" * 80)
f, (ax1, ax2) = plt.subplots(nrows=1, ncols=2, figsize=(10, 5))
f.subplots_adjust(wspace=.3, hspace=.3)
axes = (ax1, ax2)
kwargs = {
"linewidth": 2.0,
"markersize": 8,
}
plot_kwargs = {
"default": {**kwargs, "color": "black"},
"inducer": {**kwargs, "color": "green"},
"inhibitor": {**kwargs, "color": "magenta"}
}
# for all conditions
for simkey, df in dfs.items():
print(f"\t{simkey}")
for ax in axes:
# simulation type
ax.set_title(pkkey)
sim_type = simkey.split("_")[1]
x = self.Q_(df['dose'].values, df['dose_unit'][0]) * self.Mr.mid
x = x.to(unit_dose)
y = df[pkkey]
print(y)
if simkey.startswith("midpo"):
marker = "o"
linestyle = "-"
alpha = 0.5
label = f"po, {sim_type}"
elif simkey.startswith("midiv"):
marker = "s"
linestyle = "--"
alpha = 1.0
label = f"iv, {sim_type}"
ax.plot(x, y, label=label, marker=marker, linestyle=linestyle, alpha=alpha,
**plot_kwargs[sim_type])
ax.set_xlabel(f"dose [{unit_dose}]")
yunit = df[f"{pkkey}_unit"][0]
ax.set_ylabel(f"{pkkey} [{yunit}]")
#ax.legend()
ax2.set_yscale("log")
figures[f'fig_{pkkey}'] = f
return figures
'''