Ver código fonte

New template methods for states

Eric Ramat 7 anos atrás
pai
commit
1dc0fa2933

+ 5 - 0
src/artis/kernel/AbstractCoupledModel.hpp

@@ -370,6 +370,11 @@ protected:
         }
     }
 
+    template < typename Z >
+    void S(std::initializer_list < std::pair < unsigned int,
+           Z T::* > > list)
+    { States < T, U >::S(list); }
+
     void setsubmodel(unsigned int index, type* model)
     {
         if (setsubmodels.find(index) == setsubmodels.end()) {

+ 61 - 59
src/artis/kernel/States.hpp

@@ -24,6 +24,8 @@
 #define __ARTIS_KERNEL_STATES_HPP
 
 #include <artis/kernel/State.hpp>
+#include <artis/kernel/Value.hpp>
+
 #include <vector>
 
 namespace artis { namespace kernel {
@@ -38,80 +40,80 @@ public:
     virtual ~States()
     { }
 
-    virtual void restore(const State < U >& state)
-    {
-        unsigned int index = 0;
-
-        for (typename std::vector < bool T::* >::iterator it =
-                 statesB.begin(); it != statesB.end(); ++it) {
-            state.get_state(index, *it);
-            ++index;
-        }
-        index = 0;
-        for (typename std::vector < int T::* >::iterator it =
-                 statesI.begin(); it != statesI.end(); ++it) {
-            state.get_state(index, *it);
-            ++index;
-        }
-        index = 0;
-        for (typename std::vector < double T::* >::iterator it =
-                 statesD.begin(); it != statesD.end(); ++it) {
-            state.get_state(index, *it);
-            ++index;
-        }
-    }
+    const Any& get(unsigned int index) const
+    { return states.at(index); }
 
-    virtual void save(State < U >& state) const
+    template < typename V >
+    void S(std::initializer_list < std::pair < unsigned int,
+           V T::* > > list)
     {
-        unsigned int index = 0;
-
-        for (typename std::vector < bool T::* >::const_iterator it =
-                 statesB.begin(); it != statesB.end(); ++it) {
-            state.add_state(index, *it);
-            ++index;
-        }
-        index = 0;
-        for (typename std::vector < int T::* >::const_iterator it =
-                 statesI.begin(); it != statesI.end(); ++it) {
-            state.add_state(index, *it);
-            ++index;
-        }
-        index = 0;
-        for (typename std::vector < double T::* >::const_iterator it =
-                 statesD.begin(); it != statesD.end(); ++it) {
-            state.add_state(index, *it);
-            ++index;
+        for (typename std::initializer_list < std::pair < unsigned int,
+                 V T::* > >::iterator it = list.begin(); it != list.end();
+             ++it) {
+            if (states.size() <= it->first) {
+                states.resize(it->first + 1);
+            }
+            states[it->first] = it->second;
         }
     }
 
-    void stateB(unsigned int index, bool T::* var)
+    virtual void restore(const State < U >& /* state */)
     {
-        if (statesB.size() <= index) {
-            statesB.resize(index + 1);
-        }
-        statesB[index] = var;
+        // unsigned int index = 0;
+
+        // for (typename std::vector < bool T::* >::iterator it =
+        //          statesB.begin(); it != statesB.end(); ++it) {
+        //     state.get_state(index, *it);
+        //     ++index;
+        // }
+        // index = 0;
+        // for (typename std::vector < int T::* >::iterator it =
+        //          statesI.begin(); it != statesI.end(); ++it) {
+        //     state.get_state(index, *it);
+        //     ++index;
+        // }
+        // index = 0;
+        // for (typename std::vector < double T::* >::iterator it =
+        //          statesD.begin(); it != statesD.end(); ++it) {
+        //     state.get_state(index, *it);
+        //     ++index;
+        // }
     }
 
-    void stateI(unsigned int index, int T::* var)
+    virtual void save(State < U >& /* state */) const
     {
-        if (statesI.size() <= index) {
-            statesI.resize(index + 1);
-        }
-        statesI[index] = var;
+        // unsigned int index = 0;
+
+        // for (typename std::vector < bool T::* >::const_iterator it =
+        //          statesB.begin(); it != statesB.end(); ++it) {
+        //     state.add_state(index, *it);
+        //     ++index;
+        // }
+        // index = 0;
+        // for (typename std::vector < int T::* >::const_iterator it =
+        //          statesI.begin(); it != statesI.end(); ++it) {
+        //     state.add_state(index, *it);
+        //     ++index;
+        // }
+        // index = 0;
+        // for (typename std::vector < double T::* >::const_iterator it =
+        //          statesD.begin(); it != statesD.end(); ++it) {
+        //     state.add_state(index, *it);
+        //     ++index;
+        // }
     }
 
-    void state(unsigned int index, double T::* var)
+    template < typename V >
+    void state(unsigned int index, V T::* var)
     {
-        if (statesD.size() <= index) {
-            statesD.resize(index + 1);
+        if (states.size() <= index) {
+            states.resize(index + 1);
         }
-        statesD[index] = var;
+        states[index] = Any(var);
     }
 
-protected:
-    std::vector < bool T::* > statesB;
-    std::vector < int T::* > statesI;
-    std::vector < double T::* > statesD;
+private:
+    std::vector < Any > states;
 };
 
 } }

+ 20 - 0
src/test/test.cpp

@@ -87,6 +87,7 @@ class BModel : public AtomicModel < BModel >
 public:
     enum externals { IX, BX, DX };
     enum internals { IY, BY, DY };
+    enum states { N };
 
     BModel()
     {
@@ -101,6 +102,8 @@ public:
 
         internal(BY, &BModel::_by);
         internal(DY, &BModel::_dy);
+
+        S < int >({ { N, &BModel::_n } });
     }
 
     virtual ~BModel()
@@ -114,6 +117,7 @@ public:
         _iy = _ix + 1;
         _by = not _bx;
         _dy = _dx + 1;
+        ++_n;
     }
 
     void init(double /* t */, const ModelParameters& /* parameters */)
@@ -121,6 +125,7 @@ public:
         _iy = 0;
         _by = false;
         _dy = 0.;
+        _n = 0;
     }
 
 private:
@@ -133,6 +138,9 @@ private:
     int _iy;
     bool _by;
     double _dy;
+
+    // states
+    int _n;
 };
 
 class RootModel :
@@ -143,10 +151,15 @@ class RootModel :
 {
 public:
     enum submodels { A, B };
+    enum states { N };
 
     RootModel()
     {
+        // submodels
         S({ { A, &_a }, { B, &_b } });
+
+        // states
+        S < int >({ { N, &RootModel::_n } });
     }
 
     virtual ~RootModel()
@@ -160,17 +173,24 @@ public:
         _b.put < int >(t, BModel::IX, _a.get < int >(t, AModel::IX));
         _b.put < bool >(t, BModel::BX, _a.get < bool >(t, AModel::BX));
         _b(t);
+
+        ++_n;
     }
 
     void init(double t, const ModelParameters& parameters)
     {
         _a.init(t, parameters);
         _b.init(t, parameters);
+        _n = 0;
     }
 
 private:
+    // submodels
     AModel _a;
     BModel _b;
+
+    // states
+    int _n;
 };
 
 typedef artis::kernel::Simulator < RootModel,