Beispiel #1
0
"""Generates time-series drug concentration data in central compartment based on .2comp_subct_linear.mmt and saves it
to .csv file. """
import numpy as np
import pandas as pd

from PKPD.model import model as m
from PKPD.inference import inference

# generating data
file_name = 'demo/synthesised_3_compartment/3_bolus_linear.mmt'
model = m.SingleOutputModel(file_name)

# List of parameters
true_parameters = [
    0,  # central_compartment.drug
    0,  # peripheral_compartment_1.drug
    0,  # peripheral_compartment_2.drug
    1,  # central_compartment.CL
    3,  # central_compartment.Kcp1
    2,  # central_compartment.Kcp2
    5,  # central_compartment.V
    2,  # peripheral_compartment_1.Kpc
    2,  # peripheral_compartment_1.V
    2,  # peripheral_compartment_2.Kpc
    2  # peripheral_compartment_2.V
]

times = np.linspace(0.0, 24.0, 100)
model_result = model.simulate(true_parameters, times)

# add white noise to generate data
Beispiel #2
0
    def next_tab(self):
        """Switches to the simulation tab, when triggered by clicking the 'next' QPushButton on the home tab.
        """
        if self.home.is_model_file_valid and self.home.is_data_file_valid:
            try:
                # piece dataframe into ID, time, states and dose data
                self.simulation.extract_data_from_dataframe()

                # get dose schedule TODO: write test
                self.simulation.get_dose_schedule()

                # filter data from time points with no information TODO: write test
                self.simulation.filter_data()

                # TODO: move data extraction from plotting
                # add plot of dosing schedule
                # add dose schedule option button
                # list doses of patient, if available
                # allow for adding of doses

                # plot data in simulation tab
                self.simulation.add_data_to_data_model_plot()

                # disable live plotting and line removal for the simulation
                self.simulation.enable_live_plotting = False
                self.simulation.enable_line_removal = False

                # instantiate model
                if self.simulation.is_single_output_model:  # single output
                    self.model = m.SingleOutputModel(self.home.model_file)
                else:  # multi output
                    self.model = m.MultiOutputModel(self.home.model_file)

                    # set model output dimension to data dimension
                    self.model.set_output_dimension(self.simulation.data_dimension)

                # fill sliders, plot options and parameter table with parameters in model
                self.simulation.fill_parameter_slider_group()
                self.simulation.fill_plot_option_window()

                # switch to simulation tab
                self.tabs.setCurrentIndex(self.sim_tab_index)

            except ValueError:
                # generate error message
                error_message = 'The .csv file does not seem to be properly formatted. Please check again!'
                QtWidgets.QMessageBox.question(self,
                                               'Data structure not compatible!',
                                               error_message,
                                               QtWidgets.QMessageBox.Yes
                                               )

            # instantiate inverse problem (after switching to simulation tab to improve user experience)
            try:
                self._instantiate_inverse_problem()
            except Exception as e:
                warning_message = 'Warning: The initialisation of the inverse problem failed.'
                QtWidgets.QMessageBox.question(self,
                                               warning_message,
                                               str(e),
                                               QtWidgets.QMessageBox.Yes
                                               )

            # Check Units in MMT file
            try:
                self.model.model.check_units(mode=myokit.UNIT_STRICT)
            except Exception as e:  # Display Warning if Inconsistent
                warning_message = 'Warning: Units may be inconsistent'
                QtWidgets.QMessageBox.question(self, warning_message, str(e), QtWidgets.QMessageBox.Yes)
        else:
            # update file dialog icons
            if not self.home.is_model_file_valid:
                self.home.model_check_mark.setPixmap(self.rescaled_rc)
            else:
                self.home.model_check_mark.setPixmap(self.rescaled_cm)
            if not self.home.is_data_file_valid:
                self.home.data_check_mark.setPixmap(self.rescaled_rc)
            else:
                self.home.data_check_mark.setPixmap(self.rescaled_cm)

            # generate error message
            error_message = 'At least one of the files does not seem to exist or does not have the correct file ' \
                            'format. Please check again!'
            QtWidgets.QMessageBox.question(self, 'Files not found!', error_message, QtWidgets.QMessageBox.Yes)
class TestSingleOutputProblem(unittest.TestCase):
    """Testing the methods of the SingleOutputInverseProblem class.
    """
    # Test case: Linear One Compartment Model with Bolus dosing
    # generating data
    file_name = 'PKPD/modelRepository/1_bolus_linear.mmt'
    one_comp_model = m.SingleOutputModel(file_name)
    true_parameters_one_comp_model = [0, 1, 4]  # [initial drug, CL, V]

    # create protocol object
    protocol = myokit.Protocol()

    # schedule dosing event
    protocol.schedule(level=5, start=4.0, duration=4)

    times = np.linspace(0.0, 24.0, 100)
    model_result = one_comp_model.simulate(true_parameters_one_comp_model, times)

    # noise-free data, to check whether optimisation works
    data_one_comp_model = model_result

    def test_find_optimal_parameter(self):
        """Test whether the find_optimal_parameter method works as expected.
        """
        problem = inference.SingleOutputInverseProblem(models=[self.one_comp_model],
                                                       times=[self.times],
                                                       values=[self.data_one_comp_model]
                                                       )

        # start somewhere in parameter space (close to the solution for ease)
        initial_parameters = np.array([0.1, 1.1, 4.1])

        # solve inverse problem
        problem.find_optimal_parameter(initial_parameter=initial_parameters, number_of_iterations=1)
        estimated_parameters = problem.estimated_parameters

        # assert agreement of estimates with true parameters
        for parameter_id, true_value in enumerate(self.true_parameters_one_comp_model):
            estimated_value = estimated_parameters[parameter_id]
            assert true_value == pytest.approx(estimated_value, rel=0.5)

    def test_set_error_function(self):
        """Test whether the set_error_function method works as expected.
        """
        problem = inference.SingleOutputInverseProblem(models=[self.one_comp_model],
                                                       times=[self.times],
                                                       values=[self.data_one_comp_model]
                                                       )

        # iterate through valid error measures
        valid_err_func = [pints.MeanSquaredError, pints.RootMeanSquaredError, pints.SumOfSquaresError]
        for err_func in valid_err_func:
            problem.set_error_function(error_function=err_func)

            # assert that error measure is set as expected
            assert type(err_func(problem.problem_container[0])) == type(problem.error_function_container[0])

    def test_set_optimiser(self):
        """Test whether the set_optimiser method works as expected. The estimated values are not of interest but rather
        whether the optimiser are properly embedded.
        """
        problem = inference.SingleOutputInverseProblem(models=[self.one_comp_model],
                                                       times=[self.times],
                                                       values=[self.data_one_comp_model]
                                                       )

        # iterate through valid optimisers
        valid_optimisers = [pints.CMAES, pints.NelderMead, pints.PSO, pints.SNES, pints.XNES]
        for opt in valid_optimisers:
            problem.set_optimiser(optimiser=opt)

            assert opt == problem.optimiser
Beispiel #4
0
"""Generates time-series drug concentration data based on .1comp_bolus_linear.mmt and saves it to .csv file.
"""
import numpy as np
import pandas as pd

from PKPD.model import model as m
from PKPD.inference import inference

# generating data
file_name = 'demo/synthesised_1_compartment/1comp_bolus_linear.mmt'
one_comp_model = m.SingleOutputModel(file_name)
true_parameters = [0, 2, 4]  # [initial drug, CL, V]

times = np.linspace(0.0, 24.0, 100)
model_result = one_comp_model.simulate(true_parameters, times)

# add white noise to generate data
scale = np.mean(model_result) * 0.05  # arbitrary choice of noise (not too much, not too little)
data = model_result + np.random.normal(loc=0.0,
                                       scale=scale,
                                       size=len(model_result)
                                       )

df = pd.DataFrame({'time_h': times, 'concentration_ng_mL': data})
df.to_csv('demo/synthesised_1_compartment/one_compartment.csv', index=False)
Beispiel #5
0
class TestSingleOutputModel(unittest.TestCase):
    """Tests the functionality of all methods of the SingleOutputModel class.
    """
    # Test case I: 1-compartment model
    file_name = 'PKPD/modelRepository/1_bolus_linear.mmt'
    one_comp_model = m.SingleOutputModel(file_name)

    def test_init(self):
        """Tests whether the Model class initialises as expected.
        """
        # Test case I: 1-compartment model
        # expected:
        state_names = ['central_compartment.drug']
        output_name = 'central_compartment.drug_concentration'
        parameter_names = ['central_compartment.CL', 'central_compartment.V']
        number_parameters_to_fit = 3

        # assert initialised values coincide
        assert state_names == self.one_comp_model.state_names
        assert output_name == self.one_comp_model.output_name
        for parameter_id, parameter in enumerate(
                self.one_comp_model.parameter_names):
            assert parameter_names[parameter_id] == parameter
        assert number_parameters_to_fit == self.one_comp_model.number_parameters_to_fit

    def test_n_parameters(self):
        """Tests whether the n_parameter method returns the correct number of fit parameters.
        """
        # Test case I: 1-compartment model
        # expected
        n_parameters = 3

        # assert correct number of parameters is returned.
        assert n_parameters == self.one_comp_model.n_parameters()

    def test_n_outputs(self):
        """Tests whether the n_outputs method returns the correct number of outputs.
        """
        # Test case I: 1-compartment model
        # expected
        n_outputs = 1

        # assert correct number of outputs.
        assert n_outputs == self.one_comp_model.n_outputs()

    def test_simulate(self):
        """Tests whether the simulate method works as expected. Tests implicitly also whether the _set_parameters method
        works properly.
        """
        # Test case I: 1-compartment model
        parameters = [0, 2, 4]  # different from initialised parameters
        times = np.arange(25)

        # expected
        model, protocol, _ = myokit.load(self.file_name)
        model.set_state([parameters[0]])
        model.set_value('central_compartment.CL', parameters[1])
        model.set_value('central_compartment.V', parameters[2])
        simulation = myokit.Simulation(model, protocol)
        myokit_result = simulation.run(
            duration=times[-1] + 1,
            log=['central_compartment.drug_concentration'],
            log_times=times)
        expected_result = myokit_result.get(
            'central_compartment.drug_concentration')

        # assert that Model.simulate returns the same result.
        model_result = self.one_comp_model.simulate(parameters, times)

        assert np.array_equal(expected_result, model_result)