Chaste  Release::2017.1
AbstractCardiacCellWithModifiers.hpp
1 /*
2 
3 Copyright (c) 2005-2017, University of Oxford.
4 All rights reserved.
5 
6 University of Oxford means the Chancellor, Masters and Scholars of the
7 University of Oxford, having an administrative office at Wellington
8 Square, Oxford OX1 2JD, UK.
9 
10 This file is part of Chaste.
11 
12 Redistribution and use in source and binary forms, with or without
13 modification, are permitted provided that the following conditions are met:
14  * Redistributions of source code must retain the above copyright notice,
15  this list of conditions and the following disclaimer.
16  * Redistributions in binary form must reproduce the above copyright notice,
17  this list of conditions and the following disclaimer in the documentation
18  and/or other materials provided with the distribution.
19  * Neither the name of the University of Oxford nor the names of its
20  contributors may be used to endorse or promote products derived from this
21  software without specific prior written permission.
22 
23 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
24 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
27 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
28 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
29 GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
32 OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33 
34 */
35 
36 #ifndef ABSTRACTCARDIACCELLWITHMODIFIERS_HPP_
37 #define ABSTRACTCARDIACCELLWITHMODIFIERS_HPP_
38 
39 #include <boost/shared_ptr.hpp>
40 #include <map>
41 #include <string>
42 
43 #include "AbstractCvodeCell.hpp"
44 #include "AbstractCvodeCellWithDataClamp.hpp"
45 #include "AbstractCardiacCell.hpp"
46 
47 #include "AbstractModifier.hpp"
48 #include "AbstractIvpOdeSolver.hpp"
49 #include "AbstractStimulusFunction.hpp"
50 
51 #include "ChasteSerialization.hpp"
52 #include "ClassIsAbstract.hpp"
53 #include <boost/serialization/shared_ptr.hpp>
54 #include <boost/serialization/base_object.hpp>
55 #include <boost/serialization/split_member.hpp>
56 
61 template<class CARDIAC_CELL>
63 {
64 private:
73  template<class Archive>
74  void save(Archive & archive, const unsigned int version) const
75  {
76  // This calls serialize on the base class.
77  archive & boost::serialization::base_object<CARDIAC_CELL>(*this);
78 
79  // This is a bit unusual - as it contains pointers to member variables in the subclasses.
80  // So we deal with it specially on reloading below.
81  // The map is always set up in the same way, so should be in the same order, but we'll
82  // archive the names as well for testing on load to be on the safe side.
83  std::map<std::string, boost::shared_ptr<AbstractModifier>* >::const_iterator iter;
84  for (iter = mModifiersMap.begin(); iter!= mModifiersMap.end(); ++iter)
85  {
86  const boost::shared_ptr<AbstractModifier>* p_to_smart_pointer = (*iter).second;
87  const boost::shared_ptr<AbstractModifier> p_modifier = *p_to_smart_pointer;
88  archive & (*iter).first; // Name of the modifier
89  archive & p_modifier; // Modifier
90  }
91  }
98  template<class Archive>
99  void load(Archive & archive, const unsigned int version)
100  {
101  // This calls serialize on the base class.
102  archive & boost::serialization::base_object<CARDIAC_CELL>(*this);
103 
104  // We have made new smart pointers to dummy modifiers via the constructor, so instead of overwriting
105  // these pointers with new pointers (leaving a memory leak), go through and make the existing pointers
106  // point to the correct modifiers again!
107  std::map<std::string, boost::shared_ptr<AbstractModifier>* >::iterator iter;
108  for (iter = mModifiersMap.begin(); iter!= mModifiersMap.end(); ++iter)
109  {
110  boost::shared_ptr<AbstractModifier>* p_to_constructed_smart_pointer = (*iter).second;
111  boost::shared_ptr<AbstractModifier> p_loaded;
112  std::string modifier_name;
113  archive & modifier_name; // Name of the modifier
114  archive & p_loaded; // Modifier
115 
116  // Paranoia check that this is the modifier we think it is.
117  if ((*iter).first != modifier_name)
118  {
120  // You're in trouble.
121  // If this breaks, perhaps change this loop to do the right number and
122  // use modifier_name as mModifiersMap key instead.
123  }
124 
125  // Set the constructed smart pointer to be the same as the loaded one.
126  *(p_to_constructed_smart_pointer) = p_loaded;
127  }
128  }
129  BOOST_SERIALIZATION_SPLIT_MEMBER()
130 
131 
132  std::map<std::string, boost::shared_ptr<AbstractModifier>* > mModifiersMap;
133 
134 protected:
141  void AddModifier(std::string modifierName, boost::shared_ptr<AbstractModifier>& pModifier);
142 
143 public:
156  unsigned numberOfStateVariables,
157  unsigned voltageIndex,
158  boost::shared_ptr<AbstractStimulusFunction> pIntracellularStimulus);
159 
166  boost::shared_ptr<AbstractModifier> GetModifier(const std::string& rModifierName);
167 
175  bool HasModifier(const std::string& rModifierName) const;
176 
183  void SetModifier(const std::string& rModifierName, boost::shared_ptr<AbstractModifier>& pNewModifier);
184 };
185 
186 // Special case of archiving an abstract class that's templated over Chaste classes.
187 // See the comments in the top of global/src/checkpointing/ClassIsAbstract.hpp
188 namespace boost {
189 namespace serialization {
190 
191  template<class C>
192  struct is_abstract<AbstractCardiacCellWithModifiers<C> >
193  TEMPLATED_CLASS_IS_ABSTRACT_DEFN
194 
195  template<class C>
196  struct is_abstract<const AbstractCardiacCellWithModifiers<C> >
197  TEMPLATED_CLASS_IS_ABSTRACT_DEFN
198 }}
199 
200 
201 #endif // ABSTRACTCARDIACCELLWITHMODIFIERS_HPP_
void load(Archive &archive, const unsigned int version)
#define NEVER_REACHED
Definition: Exception.hpp:206
std::map< std::string, boost::shared_ptr< AbstractModifier > * > mModifiersMap
void save(Archive &archive, const unsigned int version) const
boost::shared_ptr< AbstractModifier > GetModifier(const std::string &rModifierName)
void SetModifier(const std::string &rModifierName, boost::shared_ptr< AbstractModifier > &pNewModifier)
void AddModifier(std::string modifierName, boost::shared_ptr< AbstractModifier > &pModifier)
friend class boost::serialization::access
bool HasModifier(const std::string &rModifierName) const