myokit 1.33.9__py3-none-any.whl → 1.35.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (229) hide show
  1. myokit/__init__.py +9 -36
  2. myokit/__main__.py +76 -142
  3. myokit/_aux.py +62 -16
  4. myokit/_bin/example.mmt +1 -2
  5. myokit/_bin/install-win/menu.json +7 -7
  6. myokit/_config.py +22 -31
  7. myokit/_datablock.py +30 -74
  8. myokit/_datalog.py +49 -72
  9. myokit/_err.py +25 -24
  10. myokit/_expressions.py +50 -68
  11. myokit/_io.py +15 -27
  12. myokit/_model_api.py +453 -249
  13. myokit/_myokit_version.py +1 -5
  14. myokit/_parsing.py +38 -44
  15. myokit/_progress.py +5 -8
  16. myokit/_protocol.py +99 -9
  17. myokit/_sim/__init__.py +7 -24
  18. myokit/_sim/cable.c +6 -8
  19. myokit/_sim/cable.py +6 -8
  20. myokit/_sim/cmodel.h +125 -70
  21. myokit/_sim/cmodel.py +12 -14
  22. myokit/_sim/compiler.py +1 -4
  23. myokit/_sim/cvodessim.c +196 -118
  24. myokit/_sim/cvodessim.py +130 -103
  25. myokit/_sim/differential.hpp +4 -4
  26. myokit/_sim/fiber_tissue.c +4 -8
  27. myokit/_sim/fiber_tissue.py +11 -13
  28. myokit/_sim/jacobian.cpp +2 -2
  29. myokit/_sim/jacobian.py +11 -8
  30. myokit/_sim/mcl.h +53 -55
  31. myokit/_sim/opencl.py +21 -27
  32. myokit/_sim/openclsim.c +3 -7
  33. myokit/_sim/openclsim.cl +3 -3
  34. myokit/_sim/openclsim.py +49 -40
  35. myokit/_sim/pacing.h +36 -16
  36. myokit/_sim/rhs.c +6 -13
  37. myokit/_sim/rhs.py +5 -14
  38. myokit/_sim/sundials.py +1 -4
  39. myokit/_system.py +10 -16
  40. myokit/_unit.py +4 -13
  41. myokit/float.py +0 -3
  42. myokit/formats/__init__.py +8 -10
  43. myokit/formats/ansic/__init__.py +0 -3
  44. myokit/formats/ansic/_ewriter.py +2 -4
  45. myokit/formats/ansic/_exporter.py +1 -4
  46. myokit/formats/ansic/template/cable.c +4 -4
  47. myokit/formats/ansic/template/euler.c +5 -5
  48. myokit/formats/ansic/template/sim.c +6 -6
  49. myokit/formats/axon/__init__.py +1 -3
  50. myokit/formats/axon/_abf.py +12 -17
  51. myokit/formats/axon/_atf.py +5 -6
  52. myokit/formats/axon/_importer.py +0 -3
  53. myokit/formats/cellml/__init__.py +0 -3
  54. myokit/formats/cellml/_ewriter.py +3 -6
  55. myokit/formats/cellml/_exporter.py +3 -6
  56. myokit/formats/cellml/_importer.py +1 -4
  57. myokit/formats/cellml/v1/__init__.py +0 -4
  58. myokit/formats/cellml/v1/_api.py +8 -11
  59. myokit/formats/cellml/v1/_parser.py +2 -5
  60. myokit/formats/cellml/v1/_writer.py +2 -11
  61. myokit/formats/cellml/v2/__init__.py +0 -3
  62. myokit/formats/cellml/v2/_api.py +8 -17
  63. myokit/formats/cellml/v2/_parser.py +2 -5
  64. myokit/formats/cellml/v2/_writer.py +1 -4
  65. myokit/formats/channelml/__init__.py +0 -3
  66. myokit/formats/channelml/_importer.py +11 -21
  67. myokit/formats/cpp/__init__.py +1 -3
  68. myokit/formats/cpp/_ewriter.py +0 -3
  69. myokit/formats/cuda/__init__.py +0 -3
  70. myokit/formats/cuda/_ewriter.py +2 -4
  71. myokit/formats/cuda/_exporter.py +0 -3
  72. myokit/formats/cuda/template/kernel.cu +8 -5
  73. myokit/formats/easyml/__init__.py +0 -3
  74. myokit/formats/easyml/_ewriter.py +9 -11
  75. myokit/formats/easyml/_exporter.py +2 -5
  76. myokit/formats/html/__init__.py +0 -3
  77. myokit/formats/html/_exporter.py +0 -3
  78. myokit/formats/html/_flatten.py +5 -21
  79. myokit/formats/latex/__init__.py +0 -3
  80. myokit/formats/latex/_ewriter.py +1 -4
  81. myokit/formats/latex/_exporter.py +4 -6
  82. myokit/formats/mathml/__init__.py +0 -3
  83. myokit/formats/mathml/_ewriter.py +2 -11
  84. myokit/formats/mathml/_parser.py +4 -6
  85. myokit/formats/matlab/__init__.py +0 -3
  86. myokit/formats/matlab/_ewriter.py +1 -4
  87. myokit/formats/matlab/_exporter.py +2 -5
  88. myokit/formats/matlab/template/main.m +3 -2
  89. myokit/formats/opencl/__init__.py +0 -3
  90. myokit/formats/opencl/_ewriter.py +2 -4
  91. myokit/formats/opencl/_exporter.py +2 -5
  92. myokit/formats/opencl/template/cable.c +10 -10
  93. myokit/formats/opencl/template/kernel.cl +1 -1
  94. myokit/formats/opencl/template/minilog.py +1 -1
  95. myokit/formats/python/__init__.py +0 -3
  96. myokit/formats/python/_ewriter.py +2 -5
  97. myokit/formats/python/_exporter.py +0 -3
  98. myokit/formats/python/template/sim.py +14 -14
  99. myokit/formats/sbml/__init__.py +0 -3
  100. myokit/formats/sbml/_api.py +50 -44
  101. myokit/formats/sbml/_importer.py +1 -4
  102. myokit/formats/sbml/_parser.py +2 -5
  103. myokit/formats/stan/__init__.py +0 -3
  104. myokit/formats/stan/_ewriter.py +2 -4
  105. myokit/formats/stan/_exporter.py +2 -5
  106. myokit/formats/stan/template/cell.stan +3 -3
  107. myokit/formats/sympy/__init__.py +0 -3
  108. myokit/formats/sympy/_ereader.py +1 -4
  109. myokit/formats/sympy/_ewriter.py +2 -5
  110. myokit/formats/wcp/__init__.py +0 -3
  111. myokit/formats/wcp/_wcp.py +2 -8
  112. myokit/formats/xml/__init__.py +0 -3
  113. myokit/formats/xml/_exporter.py +0 -3
  114. myokit/formats/xml/_split.py +0 -3
  115. myokit/gui/__init__.py +80 -246
  116. myokit/gui/datablock_viewer.py +103 -86
  117. myokit/gui/datalog_viewer.py +214 -66
  118. myokit/gui/explorer.py +15 -21
  119. myokit/gui/ide.py +171 -144
  120. myokit/gui/progress.py +9 -9
  121. myokit/gui/source.py +406 -375
  122. myokit/gui/vargrapher.py +2 -12
  123. myokit/lib/deps.py +12 -13
  124. myokit/lib/guess.py +3 -4
  125. myokit/lib/hh.py +20 -18
  126. myokit/lib/markov.py +21 -20
  127. myokit/lib/multi.py +1 -3
  128. myokit/lib/plots.py +20 -9
  129. myokit/pacing.py +0 -3
  130. myokit/pype.py +7 -18
  131. myokit/tests/__init__.py +3 -6
  132. myokit/tests/ansic_event_based_pacing.py +1 -4
  133. myokit/tests/ansic_fixed_form_pacing.py +3 -6
  134. myokit/tests/data/beeler-1977-model-compare-b.mmt +2 -2
  135. myokit/tests/data/clancy-1999-fitting.mmt +1 -0
  136. myokit/tests/test_aux.py +13 -28
  137. myokit/tests/test_cellml_v1_api.py +4 -19
  138. myokit/tests/test_cellml_v1_parser.py +0 -15
  139. myokit/tests/test_cellml_v1_writer.py +0 -9
  140. myokit/tests/test_cellml_v2_api.py +4 -19
  141. myokit/tests/test_cellml_v2_parser.py +0 -15
  142. myokit/tests/test_cellml_v2_writer.py +0 -9
  143. myokit/tests/test_cmodel.py +16 -22
  144. myokit/tests/test_compiler_detection.py +1 -11
  145. myokit/tests/test_component.py +108 -56
  146. myokit/tests/test_config.py +34 -67
  147. myokit/tests/test_datablock.py +1 -9
  148. myokit/tests/test_datalog.py +19 -24
  149. myokit/tests/test_dependency_checking.py +8 -23
  150. myokit/tests/test_expressions.py +0 -9
  151. myokit/tests/test_float.py +1 -5
  152. myokit/tests/test_formats.py +0 -9
  153. myokit/tests/test_formats_axon.py +1 -9
  154. myokit/tests/test_formats_cellml.py +0 -15
  155. myokit/tests/test_formats_channelml.py +0 -15
  156. myokit/tests/test_formats_easyml.py +0 -14
  157. myokit/tests/test_formats_exporters.py +1 -16
  158. myokit/tests/test_formats_expression_writers.py +1 -17
  159. myokit/tests/test_formats_html.py +0 -3
  160. myokit/tests/test_formats_importers.py +1 -16
  161. myokit/tests/test_formats_mathml_content.py +0 -9
  162. myokit/tests/test_formats_mathml_presentation.py +0 -9
  163. myokit/tests/test_formats_opencl.py +0 -10
  164. myokit/tests/test_formats_sbml.py +0 -15
  165. myokit/tests/test_formats_sympy.py +0 -9
  166. myokit/tests/test_formats_wcp.py +1 -3
  167. myokit/tests/test_io.py +27 -27
  168. myokit/tests/test_jacobian_calculator.py +6 -14
  169. myokit/tests/test_jacobian_tracer.py +0 -9
  170. myokit/tests/test_lib_deps.py +0 -9
  171. myokit/tests/test_lib_guess.py +0 -9
  172. myokit/tests/test_lib_hh.py +18 -12
  173. myokit/tests/test_lib_markov.py +21 -13
  174. myokit/tests/test_lib_multi.py +0 -9
  175. myokit/tests/test_lib_plots.py +13 -8
  176. myokit/tests/test_meta.py +0 -3
  177. myokit/tests/test_model.py +390 -96
  178. myokit/tests/test_model_building.py +44 -96
  179. myokit/tests/test_opencl_info.py +5 -14
  180. myokit/tests/test_pacing_factory.py +0 -3
  181. myokit/tests/test_pacing_system_c.py +1 -23
  182. myokit/tests/test_pacing_system_py.py +0 -9
  183. myokit/tests/test_parsing.py +139 -56
  184. myokit/tests/test_progress_reporters.py +0 -3
  185. myokit/tests/test_protocol.py +0 -9
  186. myokit/tests/test_protocol_floating_point.py +1 -10
  187. myokit/tests/test_protocol_time_series.py +82 -0
  188. myokit/tests/test_pype.py +0 -9
  189. myokit/tests/test_quantity.py +0 -9
  190. myokit/tests/test_rhs_benchmarker.py +1 -9
  191. myokit/tests/test_sbml_api.py +27 -42
  192. myokit/tests/test_sbml_parser.py +4 -19
  193. myokit/tests/test_simulation_1d.py +45 -25
  194. myokit/tests/test_simulation_cvodes.py +321 -55
  195. myokit/tests/test_simulation_cvodes_from_disk.py +0 -3
  196. myokit/tests/test_simulation_fiber_tissue.py +39 -12
  197. myokit/tests/test_simulation_log_interval.py +1 -431
  198. myokit/tests/test_simulation_opencl.py +69 -48
  199. myokit/tests/test_simulation_opencl_log_interval.py +1 -3
  200. myokit/tests/test_simulation_opencl_vs_cvode.py +1 -10
  201. myokit/tests/test_simulation_opencl_vs_sim1d.py +1 -10
  202. myokit/tests/test_system_info.py +1 -11
  203. myokit/tests/test_tools.py +0 -9
  204. myokit/tests/test_unit.py +1 -10
  205. myokit/tests/test_user_functions.py +0 -10
  206. myokit/tests/test_variable.py +231 -27
  207. myokit/tools.py +5 -21
  208. myokit/units.py +5 -3
  209. {myokit-1.33.9.dist-info → myokit-1.35.0.dist-info}/METADATA +12 -15
  210. myokit-1.35.0.dist-info/RECORD +391 -0
  211. {myokit-1.33.9.dist-info → myokit-1.35.0.dist-info}/WHEEL +1 -1
  212. {myokit-1.33.9.dist-info → myokit-1.35.0.dist-info}/entry_points.txt +0 -1
  213. myokit/_exec_new.py +0 -15
  214. myokit/_exec_old.py +0 -15
  215. myokit/_sim/cvodesim.c +0 -1551
  216. myokit/_sim/cvodesim.py +0 -674
  217. myokit/_sim/icsim.cpp +0 -563
  218. myokit/_sim/icsim.py +0 -363
  219. myokit/_sim/psim.cpp +0 -656
  220. myokit/_sim/psim.py +0 -493
  221. myokit/lib/common.py +0 -1094
  222. myokit/tests/test_lib_common.py +0 -130
  223. myokit/tests/test_simulation_cvode.py +0 -612
  224. myokit/tests/test_simulation_ic.py +0 -108
  225. myokit/tests/test_simulation_p.py +0 -223
  226. myokit-1.33.9.dist-info/RECORD +0 -403
  227. /myokit/formats/opencl/template/{test → test.sh} +0 -0
  228. {myokit-1.33.9.dist-info → myokit-1.35.0.dist-info}/LICENSE.txt +0 -0
  229. {myokit-1.33.9.dist-info → myokit-1.35.0.dist-info}/top_level.txt +0 -0
myokit/_sim/icsim.py DELETED
@@ -1,363 +0,0 @@
1
- #
2
- # Simulation that integrates the Jacobian to obtain the partial derivatives of
3
- # the state vector with respect to the initial conditions.
4
- #
5
- # This file is part of Myokit.
6
- # See http://myokit.org for copyright, sharing, and licensing details.
7
- #
8
- from __future__ import absolute_import, division
9
- from __future__ import print_function, unicode_literals
10
-
11
- import os
12
- import myokit
13
- import numpy as np
14
- import platform
15
- import warnings
16
-
17
- # Location of C template
18
- SOURCE_FILE = 'icsim.cpp'
19
-
20
-
21
- class ICSimulation(myokit.CppModule):
22
- """
23
- Runs a forward-Euler based simulation and calculates the partial
24
- derivatives of the state vector with respect to the initial conditions.
25
-
26
- This class is deprecated. Sensitivities with respect to initial conditions
27
- can now be calculated with the :class:`Simulation` class.
28
-
29
- The simulation is based on automatic differentiation implemented using a
30
- C++ data type that replaces a single scalar float with a float and a list
31
- of partial derivatives. Any operations on this pair update both the float
32
- and the set of derivatives. A normal simulation starts with a state
33
- ``y(tmin)`` and a right-hand side function (RHS) ``f(y) = dy/dt``. It then
34
- integrates ``f(y)`` from ``tmin`` to ``tmax`` resulting in an output state
35
- ``y(tmax)``. In this simulation the data type of ``f`` is replaced by a
36
- ``(f, df/dy)``, where ``df/dy`` is the matrix of partial derivatives of
37
- ``f`` with respect to ``y``. By integrating ``f`` from ``tmin`` to ``tmax``
38
- we obtain the state at ``tmax``. This can be seen as a function
39
- ``F(y(tmin))``, that gives the state at ``tmax`` given ``y(tmin)``. By
40
- integrating ``df/dy`` the derivative of ``F`` to ``y(tmin)`` is obtained.
41
- This result allows the sensitivity of the system to its initial conditions
42
- to be evaluated.
43
-
44
- N.B. The partial derivatives can not be calculated for the following
45
- functions: ``floor``, ``ceil``, ``abs``, quotients and remainders. If these
46
- are encountered the resulting derivatives will be yielded as ``NaN``.
47
- However, in many cases, these functions will only occur as part of a
48
- condition in an if statement, so the ``NaN``'s won't propagate to the final
49
- result.
50
-
51
- The model passed to the simulation is cloned and stored internally, so
52
- changes to the original model object will not affect the simulation.
53
-
54
- A protocol can be passed in as ``protocol`` or set later using
55
- :meth:`set_protocol`.
56
-
57
- Simulations maintain an internal state consisting of
58
-
59
- - the current simulation time
60
- - the current state
61
- - the derivatives of the current state with respect to the initial state
62
-
63
- When a simulation is created, the simulation time is set to 0 and the
64
- state is obtained from the given model. The initial derivatives matrix is
65
- an identity matrix of size ``(n, n)``, where ``n`` is the number of states
66
- in the model.
67
- After each call to :meth:`run` the time, state and derivative variables are
68
- updated so that each successive call to run continues where the previous
69
- one left off. A :meth:`reset` method is provided that will set the
70
- time back to 0, revert the current state to the default state and set the
71
- derivatives back to ``I``.
72
-
73
- The simulation provides two inputs a variable can bind to:
74
-
75
- ``time``
76
- This variable contains the simulation time.
77
- ``pace``
78
- This variable contains the current value of the pacing variable
79
- as given by the protocol passed to the Simulation.
80
-
81
- No labeled variables are required.
82
- """
83
- _index = 0 # Simulation id
84
-
85
- def __init__(self, model, protocol=None):
86
- super(ICSimulation, self).__init__()
87
-
88
- # Deprecated on 2021-02-25
89
- warnings.warn(
90
- 'The class `ICSimulation` is deprecated. Sensitivities with'
91
- ' respect to initial conditions can now be calculated with the'
92
- ' single cell myokit.Simulation class.')
93
-
94
- # Require a valid model
95
- if not model.is_valid():
96
- model.validate()
97
- model = model.clone()
98
- self._model = model
99
-
100
- # Set protocol
101
- self.set_protocol(protocol)
102
-
103
- # Get state and default state from model
104
- self._state = self._model.state()
105
- self._default_state = list(self._state)
106
-
107
- # Create initial list of derivatives
108
- n = len(self._state)
109
- self._deriv = [0.0] * n**2
110
- for i in range(n):
111
- self._deriv[i * (n + 1)] = 1.0
112
-
113
- # Starting time
114
- self._time = 0
115
-
116
- # Default time step
117
- self._dt = 0
118
- self.set_step_size()
119
-
120
- # Unique simulation id
121
- ICSimulation._index += 1
122
- module_name = 'myokit_ICSimulation_' + str(ICSimulation._index)
123
- module_name += '_' + str(myokit.pid_hash())
124
-
125
- # Arguments
126
- args = {
127
- 'module_name': module_name,
128
- 'model': self._model,
129
- }
130
- fname = os.path.join(myokit.DIR_CFUNC, SOURCE_FILE)
131
-
132
- # Define libraries
133
- libs = []
134
- if platform.system() != 'Windows': # pragma: no windows cover
135
- libs.append('m')
136
-
137
- # Create simulation
138
- libd = []
139
- incd = [myokit.DIR_CFUNC]
140
- self._sim = self._compile(module_name, fname, args, libs, libd, incd)
141
-
142
- def block(self, log, derivatives):
143
- """
144
- Takes the output of a simulation (a simulation log and a list of
145
- derivatives) and combines it into a single :class:`DataBlock2d` object.
146
-
147
- Each entry in the log is converted to a 0d entry in the log. The
148
- calculated derivatives are stored as the 2d field ``derivatives``.
149
- """
150
- # Get time data
151
- tvar = self._model.time().qname()
152
- try:
153
- time = log[tvar]
154
- except KeyError:
155
- raise ValueError(
156
- 'The given log must contain an entry for <' + tvar + '>.')
157
-
158
- # Check shape of derivatives array
159
- n = self._model.count_states()
160
- shape = (len(time), n, n)
161
- if derivatives.shape != shape:
162
- raise ValueError(
163
- 'Wrong input: Expecting a derivatives array of shape '
164
- + str(shape) + '.')
165
-
166
- # Create datablock
167
- block = myokit.DataBlock2d(n, n, time)
168
- for k, v in log.items():
169
- if k != tvar:
170
- block.set0d(k, v)
171
- block.set2d('derivatives', derivatives)
172
- return block
173
-
174
- def default_state(self):
175
- """
176
- Returns the default state.
177
- """
178
- return list(self._default_state)
179
-
180
- def derivatives(self):
181
- """
182
- Return the partial derivatives of the current state with respect to the
183
- initial state.
184
- """
185
- n = len(self._state)
186
- return np.array(self._deriv, copy=True).reshape((n, n))
187
-
188
- def reset(self):
189
- """
190
- Resets the simulation:
191
-
192
- - The time variable is set to 0
193
- - The state is set back to the default state
194
-
195
- """
196
- # Reset time
197
- self._time = 0
198
-
199
- # Reset state
200
- self._state = list(self._default_state)
201
-
202
- # Reset derivatives
203
- n = len(self._state)
204
- self._deriv = [0.0] * n**2
205
- for i in range(n):
206
- self._deriv[i * (n + 1)] = 1.0
207
-
208
- def run(self, duration, log=None, log_interval=5, progress=None,
209
- msg='Running ICSimulation'):
210
- """
211
- Runs a simulation and returns the logged results. Running a simulation
212
- has the following effects:
213
-
214
- - The internal state is updated to the last state in the simulation.
215
- - The simulation's time variable is updated to reflect the time
216
- elapsed during the simulation.
217
-
218
- The number of time units to simulate can be set with ``duration``.
219
-
220
- The variables to log can be indicated using the ``log`` argument. There
221
- are several options for its value:
222
-
223
- - ``None`` (default), to log all states.
224
- - An integer flag or a combination of flags. Options:
225
- ``myokit.LOG_NONE``, ``myokit.LOG_STATE``, ``myokit.LOG_INTER``,
226
- ``myokit.LOG_BOUND``.
227
- - A list of qnames or variable objects
228
- - A :class:`myokit.DataLog` obtained from a previous simulation.
229
- In this case, the newly logged data will be appended to the existing
230
- log.
231
-
232
- For more details on the ``log`` argument, see the function
233
- :meth:`myokit.prepare_log`.
234
-
235
- The method returns a :class:`myokit.DataLog` and a 3d numpy
236
- array. In the returned array, the first axis represents the time,
237
- the second axis is a state x and the third is a state y such that the
238
- point ``(t, x, y)`` represents ``dx/dy(0)`` at time t. For example, if
239
- ``p`` is the array of derivatives, to get the derivative of state 0
240
- with respect to the initial value of state 1, use ``p[:,0,1]``.
241
-
242
- A log entry is created every time *at least* ``log_interval`` time
243
- units have passed.
244
-
245
- To obtain feedback on the simulation progress, an object implementing
246
- the :class:`myokit.ProgressReporter` interface can be passed in.
247
- passed in as ``progress``. An optional description of the current
248
- simulation to use in the ProgressReporter can be passed in as `msg`.
249
- """
250
- # Simulation times
251
- if duration < 0:
252
- raise ValueError('Simulation time can\'t be negative.')
253
- tmin = self._time
254
- tmax = tmin + duration
255
-
256
- # Parse log argument
257
- log = myokit.prepare_log(
258
- log,
259
- self._model,
260
- if_empty=myokit.LOG_STATE + myokit.LOG_BOUND,
261
- allowed_classes=myokit.LOG_STATE + myokit.LOG_BOUND
262
- + myokit.LOG_INTER,
263
- )
264
-
265
- # Logging period (0 = disabled)
266
- log_interval = float(log_interval)
267
- if log_interval < 0:
268
- log_interval = 0
269
-
270
- # Create empty list for derivative lists
271
- derivs = []
272
-
273
- # Get progress indication function (if any)
274
- if progress is None:
275
- progress = myokit._Simulation_progress
276
- if progress:
277
- if not isinstance(progress, myokit.ProgressReporter):
278
- raise ValueError(
279
- 'The argument "progress" must be either a subclass of'
280
- ' myokit.ProgressReporter or None.')
281
-
282
- # Run simulation
283
- if duration > 0:
284
- # Initialize
285
- n = len(self._state)
286
- state = [0] * n
287
- deriv = [0] * (n ** 2)
288
- self._sim.sim_init(
289
- tmin,
290
- tmax,
291
- self._dt,
292
- list(self._state),
293
- list(self._deriv),
294
- state,
295
- deriv,
296
- self._protocol,
297
- log,
298
- derivs,
299
- log_interval,
300
- )
301
- t = tmin
302
- try:
303
- if progress:
304
- # Loop with feedback
305
- with progress.job(msg):
306
- r = 1 / duration
307
- while t < tmax:
308
- t = self._sim.sim_step()
309
- if not progress.update(min((t - tmin) * r, 1)):
310
- raise myokit.SimulationCancelledError()
311
- else:
312
- # Loop without feedback
313
- while t < tmax:
314
- t = self._sim.sim_step()
315
- finally:
316
- # Clean even after KeyboardInterrupt or other Exception
317
- self._sim.sim_clean()
318
- # Update internal state
319
- self._state = list(state)
320
- self._deriv = list(deriv)
321
- self._time += duration
322
- # Convert derivatives to numpy arrays
323
- # Using
324
- # derivs = [np.array(x).reshape(n,n) for x in derivs]
325
- # will create a list of views of arrays
326
- # to avoid the overhead of views, perhaps it's better to copy this
327
- # view into a new array explicitly?
328
- derivs = np.array([
329
- np.array(np.array(x).reshape(n, n), copy=True) for x in derivs
330
- ])
331
-
332
- # Return
333
- return log, derivs
334
-
335
- def set_protocol(self, protocol=None):
336
- """
337
- Changes the pacing protocol used by this simulation.
338
- """
339
- if protocol is None:
340
- self._protocol = None
341
- else:
342
- self._protocol = protocol.clone()
343
-
344
- def set_step_size(self, dt=0.01):
345
- """
346
- Sets the step size used in the forward Euler solving routine.
347
- """
348
- dt = float(dt)
349
- if dt <= 0:
350
- raise ValueError('Step size must be greater than zero.')
351
- self._dt = dt
352
-
353
- def state(self):
354
- """
355
- Returns the current state.
356
- """
357
- return list(self._state)
358
-
359
- def time(self):
360
- """
361
- Returns the current simulation time.
362
- """
363
- return self._time