LifeV
ElectroIonicModel.hpp
Go to the documentation of this file.
1 //@HEADER
2 /*
3 *******************************************************************************
4 
5  Copyright (C) 2004, 2005, 2007 EPFL, Politecnico di Milano, INRIA
6  Copyright (C) 2010 EPFL, Politecnico di Milano, Emory University
7 
8  This file is part of LifeV.
9 
10  LifeV is free software; you can redistribute it and/or modify
11  it under the terms of the GNU Lesser General Public License as published by
12  the Free Software Foundation, either version 3 of the License, or
13  (at your option) any later version.
14 
15  LifeV is distributed in the hope that it will be useful,
16  but WITHOUT ANY WARRANTY; without even the implied warranty of
17  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18  Lesser General Public License for more details.
19 
20  You should have received a copy of the GNU Lesser General Public License
21  along with LifeV. If not, see <http://www.gnu.org/licenses/>.
22 
23 *******************************************************************************
24 */
25 //@HEADER
26 
27 /*!
28  @file ElectroIonicModel
29  @brief Base class for ionic models
30 
31  This class is a abstract base class for all ionic models.
32 
33  Assume that the ionic model is written in the form
34 
35  \f[ \frac{\partial \mathbf{v} }{\partial t} = f(\mathbf{v}, t\f]
36 
37  If you wish to implement a new ionic model you should create a new
38  class which inherits from this class and implement the abstract methods:
39 
40  Given \f[ \mathbf{v} \f] compute \f[ f(\mathbf{v}, t) \f]
41  void computeRhs ( const std::vector<Real>& v, std::vector<Real>& rhs);
42  In principle this method should call the following two methods:
43 
44  Given \f[ \mathbf{v} \f] compute \f[ f(\mathbf{v}, t) \f] only for the first
45  equation, that is only for the transmembrane potential
46  Real computeLocalPotentialRhs ( const std::vector<Real>& v );
47 
48  Given \f[ \mathbf{v} \f] compute \f[ f(\mathbf{v}, t) \f] for all the variables
49  excpet the first one, that is all variables except the transmembrane potential
50  void computeGatingRhs ( const std::vector<Real>& v, std::vector<Real>& rhs );
51 
52  Print out informations about the ionic model
53  void showMe();
54 
55  Some ionic models may be solved with the Rush Larsen scheme.
56  The implementation of this method is not mandatory.
57  For biophysically detailed models, it may be convenient,
58  to have it.
59  void computeGatingVariablesWithRushLarsen ( std::vector<Real>& v, const Real dt ) {}
60 
61  @date 01-2013
62  @author Simone Rossi <simone.rossi@epfl.ch>
63 
64  @contributors
65  @mantainer Simone Rossi <simone.rossi@epfl.ch>
66  @last update 02-2012
67  */
68 
69 
70 #ifndef _ELECTROIONICMODEL_H_
71 #define _ELECTROIONICMODEL_H_
72 
73 #include <lifev/core/array/MatrixSmall.hpp>
74 #include <lifev/core/array/VectorSmall.hpp>
75 #include <lifev/core/array/VectorEpetra.hpp>
76 #include <lifev/core/array/MatrixEpetra.hpp>
77 #include <lifev/core/array/VectorElemental.hpp>
78 #include <lifev/core/fem/FESpace.hpp>
79 #include <lifev/core/array/MapEpetra.hpp>
80 
81 #include <lifev/core/util/Factory.hpp>
82 #include <lifev/core/util/FactorySingleton.hpp>
83 
84 
85 #include <lifev/electrophysiology/stimulus/ElectroStimulus.hpp>
86 
87 #include <boost/bind.hpp>
88 #include <boost/ref.hpp>
89 
90 #include <Teuchos_RCP.hpp>
91 #include <Teuchos_ParameterList.hpp>
92 #include "Teuchos_XMLParameterListHelpers.hpp"
93 
94 namespace LifeV
95 {
96 class ElectroIonicModel
97 {
98 
99 public:
100  //! @name Type definitions
101  //@{
102 
103  typedef VectorEpetra vector_Type;
104 
105  typedef std::shared_ptr<VectorEpetra> vectorPtr_Type;
106 
107  typedef std::shared_ptr<VectorElemental> elvecPtr_Type;
108 
109  typedef RegionMesh<LinearTetra> mesh_Type;
110 
111  typedef MatrixEpetra<Real> matrix_Type;
112 
113  typedef std::shared_ptr<matrix_Type> matrixPtr_Type;
114 
115  typedef FESpace<mesh_Type, MapEpetra> feSpace_Type;
116 
117  typedef std::shared_ptr<feSpace_Type> feSpacePtr_Type;
118 
119  typedef std::function < Real (const Real& t,
120  const Real& x,
121  const Real& y,
122  const Real& z,
123  const ID& i) > function_Type;
124 
125  typedef FactorySingleton<Factory<ElectroIonicModel, std::string> > IonicModelFactory;
126 
127  //@}
128 
129  //! @name Constructors & Destructor
130  //@{
131 
132  //! Empty Constructor
133  /*!
134  */
135  ElectroIonicModel();
136 
137  //! Constructor
138  /*!
139  * @param n number of equations in the ionic model
140  */
141  ElectroIonicModel ( int n );
142 
143  //! Constructor
144  /*!
145  * If the number of gating variables is unknown use the method ElectroIonicModel ( int n );
146  */
147  /*!
148  * @param n number of equations in the ionic model
149  * @param g number of gating variables in the ionic model
150  */
151  ElectroIonicModel ( int n, int g );
152 
153  //! Copy Constructor
154  /*!
155  * @param Ionic an ionic model
156  */
157  ElectroIonicModel ( const ElectroIonicModel& Ionic );
158 
159  //! Destructor
160  virtual ~ElectroIonicModel() {};
161 
162  //@}
163 
164  //! @name Methods
165  //@{
166 
167  //! setup the parameters of the ionic model from an xml file
168  /*!
169  * @param parameterList Teuchos parameter list
170  */
171  virtual void setup( Teuchos::ParameterList& parameterList) { }
172 
173  //! returns the number of equations of the ionic model
174  /*!
175  * @param
176  */
177  inline const short int Size() const
178  {
179  return M_numberOfEquations;
180  }
181 
182  //! returns the number of gating variables in the ionic model
183  /*!
184  * @param
185  */
186  inline const short int numberOfGatingVariables() const
187  {
188  return M_numberOfGatingVariables;
189  }
190 
191  //! returns the value of the membrane capacitance in the model
192  /*!
193  * @param
194  */
195  inline const Real membraneCapacitance() const
196  {
197  return M_membraneCapacitance;
198  }
199 
200  //! returns the value of the applied current in the model/point
201  /*!
202  * @param
203  */
204  inline const Real appliedCurrent() const
205  {
206  return M_appliedCurrent;
207  }
208 
209  //! returns the pointer to the applied current FE vector in the 3D case
210  /*!
211  * @param
212  */
213  inline vectorPtr_Type appliedCurrentPtr()
214  {
215  return M_appliedCurrentPtr;
216  }
217 
218  //! returns the vector with the resting values of the variables in the ionic model
219  /*!
220  * @param
221  */
222  inline const std::vector<Real> restingConditions() const
223  {
224  return M_restingConditions;
225  }
226 
227  //! returns the function describing the pacing protocol for the ionic model
228  /*!
229  * @param
230  */
231  inline const function_Type pacaingProtocol() const
232  {
233  return M_pacingProtocol;
234  }
235 
236  //! set the membrane capacitance in the ionic model
237  /*!
238  * @param p membrane capacitance
239  */
240  inline void setMembraneCapacitance ( const Real p )
241  {
242  M_membraneCapacitance = p;
243  }
244 
245  //! set the applied current in the ionic model/point
246  /*!
247  * @param p applied current magnitude
248  */
249  inline void setAppliedCurrent (const Real p)
250  {
251  M_appliedCurrent = p;
252  }
253 
254  //! set the pointer to the applied current in the 3D ionic model
255  /*!
256  * @param p applied current magnitude
257  */
258  inline void setAppliedCurrentPtr (const vectorPtr_Type p)
259  {
260  this->M_appliedCurrentPtr = p;
261  }
262 
263  //! set the pointer to the applied current in the 3D ionic model
264  /*!
265  * @param p applied current magnitude
266  */
267  inline void setAppliedCurrent (const vector_Type& p)
268  {
269  M_appliedCurrentPtr.reset ( new vector_Type ( p ) );
270  }
271 
272  //! Interpolate the function f on the FE space feSpacePtr at time time
273  /*!
274  * This method is a wrapper of the interpolation method from the FESpace class
275  */
276  /*!
277  * @param f boost function f(t,x,y,x,ID)
278  * @param feSpacePtr pointer to the finite element space on which we interpolate
279  * @param time time at which we evaluate the boost function f
280  */
281  inline void setAppliedCurrentFromFunction (function_Type& f, feSpacePtr_Type feSpacePtr,
282  Real time = 0.0)
283  {
284 
285  feSpacePtr -> interpolate (
286  static_cast<FESpace<RegionMesh<LinearTetra>, MapEpetra>::function_Type> (f),
287  *M_appliedCurrentPtr, time);
288  }
289 
290  //! Interpolate the function of the electro stimulus
291  /*!
292  * This method is a wrapper of the interpolation method from the FESpace class
293  */
294  /*!
295  * @param stimulus pacing protocol defined as ElectroStimulus boost function f(t,x,y,x,ID)
296  * @param feSpacePtr pointer to the finite element space on which we interpolate
297  * @param time time at which we evaluate the boost function f
298  */
299  inline void setAppliedCurrentFromElectroStimulus ( ElectroStimulus& stimulus, feSpacePtr_Type feSpacePtr, Real time = 0.0)
300  {
301 
302  // boost::ref() is needed here because otherwise a copy of the base object is reinstantiated
303  function_Type f = std::bind (&ElectroStimulus::appliedCurrent, boost::ref (stimulus), std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4, std::placeholders::_5 );
304 
305  feSpacePtr -> interpolate (
306  static_cast<FESpace<RegionMesh<LinearTetra>, MapEpetra>::function_Type> (f),
307  *M_appliedCurrentPtr, time);
308  }
309 
310  //! Set the pacing protocol as boost function
311  /*!
312  * @param pacingProtocol boost function defining the pacing protocol
313  */
314  inline void setPacingProtocol ( function_Type pacingProtocol )
315  {
316  M_pacingProtocol = pacingProtocol;
317  }
318 
319  //! Set component of the resting conditions
320  /*!
321  * @param value value of the resting condition
322  * @param j number of the component to be changed
323  */
324  inline void setRestingCondtions (Real value, int j)
325  {
326  M_restingConditions[j] = value;
327  }
328 
329  //! Set resting conditions
330  /*!
331  * @param restingCondition values of the resting condition
332  */
333  inline void setRestingCondtions (std::vector<Real>& restingConditions)
334  {
335  M_restingConditions = restingConditions;
336  }
337 
338  //! Simple wrapper to add the applied current
339  /*!
340  * @param rhs right hand side of the voltage equation
341  */
342  inline void addAppliedCurrent (Real& rhs)
343  {
344  rhs += M_appliedCurrent;
345  }
346 
347  //! Simple wrapper to add the applied current
348  /*!
349  * @param rhs right hand side of the ionic model (in a point)
350  */
351  inline void addAppliedCurrent (std::vector<Real>& rhs)
352  {
353  rhs[0] += M_appliedCurrent;
354  }
355 
356  //@}
357 
358  //! This methods computes the Jacobian numerically
359  /*!
360  * @param v vector of pointers to the state variables vectors
361  * @param h differentiation step
362  */
363  virtual matrix_Type getJac (const vector_Type& v, Real h = 1.0e-8);
364 
365  //! This methods computes the Jacobian numerically
366  /*!
367  * @param v vector of the state variables
368  * @param h differentiation step
369  */
370  virtual std::vector< std::vector<Real> > getJac (const std::vector<Real>& v, Real h = 1.0e-8);
371 
372  //! This methods computes the right hand side of the gating variables in the 3D case
373  /*!
374  * In 3D the gating variables are still treated nodewise (that is, as a local 0D system)
375  * It computes the right hand side of all state variables except for the voltage equation.
376  */
377  /*!
378  * @param v vector of pointers to the state variables vectors
379  * @param rhs vector of pointers to the right hand side vectors of each variable
380  */
381  virtual void computeGatingRhs ( const std::vector<vectorPtr_Type>& v, std::vector<vectorPtr_Type>& rhs );
382 
383  //! This methods computes the right hand side of the state variables that are not gating variables in the 3D case
384  /*!
385  * This method is to be used together with Rush-Larsen time advancing scheme.
386  * In 3D the non gating variables are still treated nodewise (that is, as a local 0D system).
387  * It computes the right hand side of all non gating state variables except for the voltage equation.
388  */
389  /*!
390  * @param v vector of pointers to the state variables vectors
391  * @param rhs vector of pointers to the right hand side vectors of each variable
392  */
393  virtual void computeNonGatingRhs ( const std::vector<vectorPtr_Type>& v, std::vector<vectorPtr_Type>& rhs );
394 
395  //! Compute the new value of the gating variables in 3D with the Rush Larsen method specified in the 0D version of the ionic model
396  /*!
397  * This method wraps the 0D model to be used in 3D
398  */
399  /*!
400  * @param v vector of pointers to the state variables vectors
401  * @param dt time step
402  */
403  virtual void computeGatingVariablesWithRushLarsen ( std::vector<vectorPtr_Type>& v, const Real dt );
404 
405  //! Compute the right hand side of the ionic model in 3D
406  /*!
407  * This method wraps the 0D model to be used in 3D
408  */
409  /*!
410  * @param v vector of pointers to the state variables vectors
411  * @param rhs vector of right hand side state variables
412  */
413  virtual void computeRhs ( const std::vector<vectorPtr_Type>& v, std::vector<vectorPtr_Type>& rhs );
414 
415  //! Compute the right hand side of the voltage equation linearly interpolating the ionic currents
416  /*!
417  * @param v vector of pointers to the state variables vectors
418  * @param rhs vector of right hand side state variables
419  * @param massMatrix mass matrix of the monodomain system (may be lumped)
420  */
421  virtual void computePotentialRhsICI ( const std::vector<vectorPtr_Type>& v,
422  std::vector<vectorPtr_Type>& rhs,
423  matrix_Type& massMatrix );
424 
425  //! Compute the right hand side of the voltage equation using SVI
426  /*!
427  * @param v vector of pointers to the state variables vectors
428  * @param rhs vector of right hand side state variables
429  * @param uFESpace finite element space of the voltage
430 
431  */
432  virtual void computePotentialRhsSVI ( const std::vector<vectorPtr_Type>& v,
433  std::vector<vectorPtr_Type>& rhs,
434  FESpace<mesh_Type, MapEpetra>& uFESpace );
435 
436  //! Compute the right hand side of the voltage equation using SVI specifying the quadrature rule
437  /*!
438  * @param v vector of pointers to the state variables vectors
439  * @param rhs vector of right hand side state variables
440  * @param uFESpace finite element space of the voltage
441  * @param qr quadrature rule for the integration
442  */
443  virtual void computePotentialRhsSVI ( const std::vector<vectorPtr_Type>& v,
444  std::vector<vectorPtr_Type>& rhs,
445  FESpace<mesh_Type, MapEpetra>& uFESpace,
446  const QuadratureRule& qr );
447 
448  //! Initialize the ionic model with a given vector of state variable (0D version)
449  /*!
450  * @param v vector of state variables initial conditions
451  */
452  virtual void initialize ( std::vector<Real>& v );
453 
454  //initialize with given conditions
455  //! Initialize the ionic model in 3D with a given vector of state variable vector pointers
456  /*!
457  * @param v vector of state variables initial conditions
458  */
459  virtual void initialize ( std::vector<vectorPtr_Type>& v );
460 
461 
462  //! @name Overloads
463  //@{
464 
465  //! Assignment operator
466  /*!
467  * @param Ionic ionic model
468  */
469  ElectroIonicModel& operator= ( const ElectroIonicModel& Ionic );
470 
471  //@}
472 
473 
474 
475  /////////////////////////////////////////////////////////////
476  /// A new ionic model must have the following methods ///
477  /////////////////////////////////////////////////////////////
478 
479  //! This methods contains the actual evaluation of the rhs of all state variables except for the voltage equation (0D version)
480  /*!
481  * @param v vector of state variables including the voltage (with n elements)
482  * @param rhs vector of right hand side state variables excluding the voltage (with n-1 elements)
483  */
484  virtual void computeGatingRhs ( const std::vector<Real>& v, std::vector<Real>& rhs ) = 0;
485 
486  //! This methods contains the actual evaluation of the rhs of the voltage equation only (0D version)
487  /*!
488  * @param v vector of state variables including the voltage (with n elements)
489  */
490  virtual Real computeLocalPotentialRhs ( const std::vector<Real>& v ) = 0;
491 
492  //! This methods contains the actual evaluation of the rhs of all state variablesin the model (0D version)
493  /*!
494  * Although this method can just wrap the computeGatingRhs ( const std::vector<Real>& v, std::vector<Real>& rhs ) and
495  * the computeLocalPotentialRhs ( const std::vector<Real>& v ) methods, for efficiency it may be better to duplicate the code.
496  */
497  /*!
498  * @param v vector of state variables including the voltage (with n elements)
499  * @param rhs vector of right hand side state variables including the voltage (with n elements)
500  */
501  virtual void computeRhs ( const std::vector<Real>& v, std::vector<Real>& rhs) = 0;
502 
503  //! This methods shows the parameters of the ionic model
504  /*!
505  * @param
506  */
507  virtual void showMe() = 0;
508 
509  //! This methods contains the actual evaluation of the rhs of the voltage equation only (0D version)
510  /*!
511  * Overload this method in order to solve the ionic model with the Rush-Larsen method in the monodomain solver
512  */
513  /*!
514  * @param v vector of state variables
515  * @param dt time step of the simulation
516  */
517  virtual void computeGatingVariablesWithRushLarsen ( std::vector<Real>& /*v*/, const Real /*dt*/ ) {}
518 
519 
520  //! In the case this method is improperly used, it should use this default implementation
521  /*!
522  * This method should be used together with the Rush-Larsen time advancing scheme
523  */
524  /*!
525  * @param v vector of state variables including the voltage (with n elements)
526  * @param rhs vector of right hand side state variables excluding the voltage and the gating variables (with n-g-1 elements)
527  */
528  virtual void computeNonGatingRhs ( const std::vector<Real>& v, std::vector<Real>& rhs )
529  {
530  if (M_numberOfGatingVariables == 0 )
531  {
532  computeGatingRhs (v, rhs);
533  }
534  };
535 
536  //@}
537 
538 protected:
539 
540  //Number of equations in the model
541  short int M_numberOfEquations;
542 
543  //Number of gating variables in the model
544  short int M_numberOfGatingVariables;
545 
546  //Resting conditions or default initial conditions of the ionic model
547  std::vector<Real> M_restingConditions;
548 
549  //Value of the membrane capacitance in the ionic model
550  Real M_membraneCapacitance;
551 
552  //Applied current in the 0D version and applied current in a point in the 3D version
553  Real M_appliedCurrent;
554 
555  //Pointer to the applied current FE vector for 3D simulations
556  vectorPtr_Type M_appliedCurrentPtr;
557 
558  //Function describing the pacing protocol of the model - NEEDS TO BE CONFIRMED
559  function_Type M_pacingProtocol;
560 
561 
562 };
563 
564 
565 }
566 
567 #endif
VectorEpetra - The Epetra Vector format Wrapper.
void importFromHDF5(std::string const &fileName, std::string const &matrixName="matrix")
Read a matrix from a HDF5 (.h5) file.
void updateInverseJacobian(const UInt &iQuadPt)
Epetra_Import const & importer()
Getter for the Epetra_Import.
Definition: MapEpetra.cpp:394
double Real
Generic real data.
Definition: LifeV.hpp:175
QuadratureRule - The basis class for storing and accessing quadrature rules.