Source code for iocbio.kinetics.calc.mm

import scipy.optimize
import numpy as np
from PyQt5.QtCore import pyqtSignal, QObject

from .generic import AnalyzerGeneric, XYData, Stats
from iocbio.kinetics.constants import database_table_roi, database_table_experiment


[docs]class AnalyzerMM: """Michaelis-Menten kinetics fitter""" @staticmethod def mm(x, km, vmax): return vmax*x/(km + x) def __init__(self, x, y): AnalyzerGeneric.__init__(self, x, y) self.vmax, self.km = None, None def fit(self): if self.experiment.x.size < 2: self.vmax, self.km = None, None self.calc = XYData(None, None) return # not enough data x = [1,1] r = scipy.optimize.leastsq( self.error, x ) self.vmax, self.km = r[0][0], abs(r[0][1]) xmx = self.experiment.x.max() stps = 100 xx = np.arange(0, xmx + 2*xmx/stps, xmx/stps) self.calc = XYData(xx, AnalyzerMM.mm(xx, self.km, self.vmax)) def error(self, x): vmax = x[0] km = abs(x[1]) y = self.experiment.y - AnalyzerMM.mm(self.experiment.x, km, vmax) return y
############################################################## # kinetics analysis using Michaelis-Menten relationship # and taking into account offset induced by V0 class AnalyzerMMDatabaseSignals(QObject): sigUpdate = pyqtSignal() class AnalyzerMMDatabase(AnalyzerMM): @staticmethod def database_schema(db, tablename): db.query("CREATE TABLE IF NOT EXISTS " + db.table(tablename) + "(experiment_id text PRIMARY KEY, " + "vmax double precision, km double precision, " + "FOREIGN KEY (experiment_id) REFERENCES " + db.table(database_table_experiment) + "(experiment_id) ON DELETE CASCADE" + ")") def __init__(self, database, table_name, table_source, experiment_id): self.database_schema(database, table_name) AnalyzerMM.__init__(self, [], []) # start with empty data self.signals = AnalyzerMMDatabaseSignals() self.database = database self.table_name = table_name self.table_source = table_source self.experiment_id = experiment_id self.get_data() self.fit() def get_data(self): c = self.database v0 = 0 v = [] conc = [] for row in c.query("SELECT rate, event_name, event_value FROM " + self.database.table(self.table_source) + " WHERE experiment_id=:experiment_id", experiment_id = self.experiment_id): r = row.rate n = row.event_name c = row.event_value if n == "V0": v0 = r elif c is not None: v.append(r) conc.append(c) v = np.array(v) conc = np.array(conc) v = v - v0 self.experiment = XYData(conc, v) def fit(self): AnalyzerMM.fit(self) c = self.database if self.database.has_record(self.table_name, experiment_id=self.experiment_id): c.query("UPDATE " + self.database.table(self.table_name) + " SET vmax=:vmax, km=:km WHERE experiment_id=:experiment_id", vmax=self.vmax, km=self.km, experiment_id=self.experiment_id) else: c.query("INSERT INTO " + self.database.table(self.table_name) + "(experiment_id, vmax, km) VALUES(:experiment_id,:vmax,:km)", experiment_id=self.experiment_id, vmax=self.vmax, km=self.km) self.stats['Max'] = Stats("Max", "unit/min", self.vmax) self.stats['Km'] = Stats("Km", "mM or other unit", self.km) self.signals.sigUpdate.emit() def update(self): self.get_data() self.fit()