codexventricular-compliance-operating-point.py
ventricular-compliance-operating-point.py
"""Illustrate local compliance on one stipulated passive chamber curve.
Run from the mirrored media directory. The numerical example is not patient
data or a normal range. Python 3.14, NumPy 2.3.5, Matplotlib 3.10.7.
"""
from pathlib import Path
import matplotlib
matplotlib.use("Agg")
import matplotlib.pyplot as plt
import numpy as np
A_MMHG = 2.0
K_PER_ML = 0.025
V0_ML = 60.0
OUTPUT = "ventricular-compliance-operating-point.png"
def pressure(volume_ml):
return A_MMHG * np.expm1(K_PER_ML * (volume_ml - V0_ML))
def compliance(pressure_mmhg):
return 1.0 / (K_PER_ML * (pressure_mmhg + A_MMHG))
def main():
p_marks = np.array([6.0, 14.0])
v_marks = V0_ML + np.log1p(p_marks / A_MMHG) / K_PER_ML
c_marks = compliance(p_marks)
np.testing.assert_allclose(pressure(v_marks), p_marks)
np.testing.assert_allclose(c_marks, [5.0, 2.5])
# Verify that compliance is the reciprocal local pressure derivative.
delta_v = 1e-3
derivative = (pressure(v_marks + delta_v) - pressure(v_marks - delta_v)) / (2 * delta_v)
np.testing.assert_allclose(1 / derivative, c_marks, rtol=1e-8)
plt.rcParams.update({"font.size": 10, "axes.spines.top": False, "axes.spines.right": False})
fig, (left, right) = plt.subplots(1, 2, figsize=(8, 4.8), dpi=100, facecolor="white")
fig.suptitle("Different local compliance on the same chamber curve", fontsize=13)
volume = np.linspace(65, 155, 400)
left.plot(volume, pressure(volume), color="#334155", lw=2)
left.set(xlabel="Volume V (mL)", ylabel="Distending pressure p (mmHg)", xlim=(65, 155), ylim=(0, 22))
left.set_title(r"$p=2[e^{0.025(V-60)}-1]$", fontsize=11)
for vp, pp, cp, color in zip(v_marks, p_marks, c_marks, ["#007c91", "#ba4d00"]):
segment_v = np.linspace(vp - 12, vp + 12, 40)
left.plot(segment_v, pp + (segment_v - vp) / cp, color=color, ls="--", lw=1.5)
left.scatter([vp], [pp], s=38, color=color, zorder=3)
left.annotate(f"C = {cp:g} mL/mmHg", (vp, pp), xytext=(-35, 17), textcoords="offset points", color=color, fontsize=9)
p_grid = np.linspace(2, 20, 400)
right.plot(p_grid, compliance(p_grid), color="#334155", lw=2)
right.set(xlabel="Distending pressure p (mmHg)", ylabel="Local compliance C (mL/mmHg)", xlim=(2, 20), ylim=(0, 11))
right.set_title(r"$C=dV/dp=1/[0.025(p+2)]$", fontsize=11)
for pp, cp, color in zip(p_marks, c_marks, ["#007c91", "#ba4d00"]):
right.scatter([pp], [cp], s=38, color=color, zorder=3)
right.annotate(f"({pp:g}, {cp:g})", (pp, cp), xytext=(7, 8), textcoords="offset points", color=color, fontsize=9)
for ax in (left, right):
ax.grid(alpha=0.18)
fig.text(0.5, 0.035, "Original model example; dashed lines are local tangents. Not measured data or reference ranges.", ha="center", fontsize=9)
fig.subplots_adjust(left=0.085, right=0.975, bottom=0.17, top=0.79, wspace=0.33)
fig.savefig(Path.cwd() / OUTPUT, facecolor="white", transparent=False)
plt.close(fig)
if __name__ == "__main__":
main()