From 5aa04a09ab9a076d498871145bb574c92b34541f Mon Sep 17 00:00:00 2001
From: Thomas Purcell <purcell@fhi-berlin.mpg.de>
Date: Wed, 3 Jun 2020 22:56:01 +0200
Subject: [PATCH] Fixed Memory Leak

Node and OperatorNode get virtual destructors
---
 .../feature_space/FeatureSpace.cpp            | 44 +++++++++++--------
 src/feature_creation/node/FeatureNode.cpp     |  3 +-
 src/feature_creation/node/FeatureNode.hpp     | 33 ++++++--------
 src/feature_creation/node/Node.cpp            |  4 +-
 src/feature_creation/node/Node.hpp            | 33 +++++++-------
 .../node/operator_nodes/OperatorNode.cpp      | 12 ++---
 .../node/operator_nodes/OperatorNode.hpp      | 22 +++++-----
 .../absolute_difference.hpp                   | 13 +++---
 .../allowed_operator_nodes/absolute_value.hpp | 12 ++---
 .../allowed_operator_nodes/add.hpp            | 12 ++---
 .../allowed_operator_nodes/cos.hpp            | 12 ++---
 .../allowed_operator_nodes/cube.hpp           | 13 +++---
 .../allowed_operator_nodes/cube_root.hpp      | 12 ++---
 .../allowed_operator_nodes/divide.hpp         | 12 ++---
 .../allowed_operator_nodes/exponential.hpp    | 12 ++---
 .../allowed_operator_nodes/inverse.hpp        | 13 +++---
 .../allowed_operator_nodes/log.hpp            | 13 +++---
 .../allowed_operator_nodes/multiply.hpp       | 13 +++---
 .../negative_exponential.hpp                  | 13 +++---
 .../allowed_operator_nodes/sin.hpp            | 13 +++---
 .../allowed_operator_nodes/sixth_power.hpp    | 13 +++---
 .../allowed_operator_nodes/square.hpp         | 12 ++---
 .../allowed_operator_nodes/square_root.hpp    | 14 +++---
 .../allowed_operator_nodes/subtract.hpp       | 14 +++---
 24 files changed, 179 insertions(+), 188 deletions(-)

diff --git a/src/feature_creation/feature_space/FeatureSpace.cpp b/src/feature_creation/feature_space/FeatureSpace.cpp
index 5877355c..1f262dec 100644
--- a/src/feature_creation/feature_space/FeatureSpace.cpp
+++ b/src/feature_creation/feature_space/FeatureSpace.cpp
@@ -1,22 +1,22 @@
 #include <feature_creation/feature_space/FeatureSpace.hpp>
-BOOST_CLASS_EXPORT(FeatureNode)
-BOOST_CLASS_EXPORT(AddNode)
-BOOST_CLASS_EXPORT(SubNode)
-BOOST_CLASS_EXPORT(AbsDiffNode)
-BOOST_CLASS_EXPORT(MultNode)
-BOOST_CLASS_EXPORT(DivNode)
-BOOST_CLASS_EXPORT(SqNode)
-BOOST_CLASS_EXPORT(SqrtNode)
-BOOST_CLASS_EXPORT(CbNode)
-BOOST_CLASS_EXPORT(CbrtNode)
-BOOST_CLASS_EXPORT(SixPowNode)
-BOOST_CLASS_EXPORT(ExpNode)
-BOOST_CLASS_EXPORT(NegExpNode)
-BOOST_CLASS_EXPORT(LogNode)
-BOOST_CLASS_EXPORT(AbsNode)
-BOOST_CLASS_EXPORT(InvNode)
-BOOST_CLASS_EXPORT(SinNode)
-BOOST_CLASS_EXPORT(CosNode)
+BOOST_CLASS_EXPORT_GUID(FeatureNode, "FeatureNode")
+BOOST_CLASS_EXPORT_GUID(AddNode, "AddNode")
+BOOST_CLASS_EXPORT_GUID(SubNode, "SubNode")
+BOOST_CLASS_EXPORT_GUID(AbsDiffNode, "AbsDiffNode")
+BOOST_CLASS_EXPORT_GUID(MultNode, "MultNode")
+BOOST_CLASS_EXPORT_GUID(DivNode, "DivNode")
+BOOST_CLASS_EXPORT_GUID(SqNode, "SqNode")
+BOOST_CLASS_EXPORT_GUID(SqrtNode, "SqrtNode")
+BOOST_CLASS_EXPORT_GUID(CbNode, "CbNode")
+BOOST_CLASS_EXPORT_GUID(CbrtNode, "CbrtNode")
+BOOST_CLASS_EXPORT_GUID(SixPowNode, "SixPowNode")
+BOOST_CLASS_EXPORT_GUID(ExpNode, "ExpNode")
+BOOST_CLASS_EXPORT_GUID(NegExpNode, "NegExpNode")
+BOOST_CLASS_EXPORT_GUID(LogNode, "LogNode")
+BOOST_CLASS_EXPORT_GUID(AbsNode, "AbsNode")
+BOOST_CLASS_EXPORT_GUID(InvNode, "InvNode")
+BOOST_CLASS_EXPORT_GUID(SinNode, "SinNode")
+BOOST_CLASS_EXPORT_GUID(CosNode, "CosNode")
 
 FeatureSpace::FeatureSpace(
     std::shared_ptr<MPI_Interface> mpi_comm,
@@ -140,6 +140,7 @@ void FeatureSpace::generate_feature_space()
                     ++feat_ind;
                 }
             }
+
             if(nn <= _n_rung_store)
             {
                 // bool use_temp = (nn != _max_phi) || (_max_phi > _n_rung_store);
@@ -153,9 +154,11 @@ void FeatureSpace::generate_feature_space()
         {
             std::vector<size_t> next_phi_sizes;
             mpi::all_gather(*_mpi_comm, next_phi.size(), next_phi_sizes);
+
             size_t n_feat = std::accumulate(next_phi_sizes.begin(), next_phi_sizes.end(), _phi.size());
             size_t n_feat_rank = n_feat / _mpi_comm->size();
             size_t n_feat_below_rank = _mpi_comm->rank() * n_feat_rank;
+
             if(_mpi_comm->rank() < n_feat % _mpi_comm->size())
             {
                 ++n_feat_rank;
@@ -165,6 +168,7 @@ void FeatureSpace::generate_feature_space()
             {
                 n_feat_below_rank += n_feat % _mpi_comm->size();
             }
+
             if(n_feat_below_rank + n_feat_rank <= _phi.size())
             {
                 _phi.erase(_phi.begin(), _phi.begin() + n_feat_below_rank);
@@ -178,12 +182,14 @@ void FeatureSpace::generate_feature_space()
             {
                 _phi = {};
             }
+
             while((_phi.size() < n_feat_rank) && (next_phi.size() > 0))
             {
                 next_phi.back()->reindex(_phi.size() + n_feat_below_rank);
                 _phi.push_back(next_phi.back());
                 next_phi.pop_back();
             }
+
             // This can be calculated without an all_gather, using it to not introduce too many things at one time
             std::vector<size_t> next_phi_needed;
             std::vector<size_t> next_phi_excess;
@@ -229,7 +235,7 @@ void FeatureSpace::generate_feature_space()
             }
             else
             {
-                size_t total_recv = std::accumulate(next_phi_excess.begin(), next_phi_excess.begin() + _mpi_comm->rank(), 0);
+                size_t total_recv = std::accumulate(next_phi_needed.begin(), next_phi_needed.begin() + _mpi_comm->rank(), 0);
                 size_t prev_recv_sent = 0;
                 size_t recv_size = 0;
                 int ind = 0;
diff --git a/src/feature_creation/node/FeatureNode.cpp b/src/feature_creation/node/FeatureNode.cpp
index 490b2b86..5119ad54 100644
--- a/src/feature_creation/node/FeatureNode.cpp
+++ b/src/feature_creation/node/FeatureNode.cpp
@@ -11,8 +11,7 @@ FeatureNode::FeatureNode(int feat_ind, std::string expr, std::vector<double> val
     std::copy_n(value.data(), value.size(), value_ptr());
 }
 
-FeatureNode::FeatureNode(const FeatureNode &o) :
-    Node(o)
+FeatureNode::~FeatureNode()
 {}
 
 void FeatureNode::update_add_sub_leaves(std::map<std::string, int>& add_sub_leaves, int pl_mn, int& expected_abs_tot)
diff --git a/src/feature_creation/node/FeatureNode.hpp b/src/feature_creation/node/FeatureNode.hpp
index e31596b2..89b8a7a2 100644
--- a/src/feature_creation/node/FeatureNode.hpp
+++ b/src/feature_creation/node/FeatureNode.hpp
@@ -17,6 +17,19 @@ class FeatureNode: public Node
 {
     friend class boost::serialization::access;
 
+    /**
+     * @brief Serialization function to send over MPI
+     *
+     * @param ar Archive representation of node
+     */
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<Node>(*this);
+        ar & _expr;
+        ar & _unit;
+    }
+
 protected:
     std::string _expr; //!< Expression of the feature
     Unit _unit; //!< Unit for the feature
@@ -37,12 +50,7 @@ public:
      */
     FeatureNode(int feat_ind, std::string expr, std::vector<double> value, Unit unit);
 
-    /**
-     * @brief Copy constructor
-     *
-     * @param o Node to be copied
-     */
-    FeatureNode(const FeatureNode &o);
+    ~FeatureNode();
 
     /**
      * @brief Get the expression for the overall descriptor (From head node down)
@@ -103,19 +111,6 @@ public:
      * @param add_sub_leaves [description]
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    /**
-     * @brief Serialization function to send over MPI
-     *
-     * @param ar Archive representation of node
-     */
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        ar & boost::serialization::base_object<Node>(*this);
-        ar & _expr;
-        ar & _unit;
-    }
 };
 
 #endif
diff --git a/src/feature_creation/node/Node.cpp b/src/feature_creation/node/Node.cpp
index 509d6c52..c75e1d50 100644
--- a/src/feature_creation/node/Node.cpp
+++ b/src/feature_creation/node/Node.cpp
@@ -8,9 +8,7 @@ Node::Node(int feat_ind, int n_samp) :
     _feat_ind(feat_ind)
 {}
 
-Node::Node(const Node &o) :
-    _n_samp(o._n_samp),
-    _feat_ind(o._feat_ind)
+Node::~Node()
 {}
 
 BOOST_SERIALIZATION_ASSUME_ABSTRACT(Node)
diff --git a/src/feature_creation/node/Node.hpp b/src/feature_creation/node/Node.hpp
index d03d8ac9..df7f2bd9 100644
--- a/src/feature_creation/node/Node.hpp
+++ b/src/feature_creation/node/Node.hpp
@@ -21,6 +21,20 @@
  */
 class Node
 {
+    friend class boost::serialization::access;
+
+    /**
+     * @brief Serialization function to send over MPI
+     *
+     * @param ar Archive representation of node
+     */
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & _n_samp;
+        ar & _feat_ind;
+    }
+
 protected:
     int _n_samp; //!< Number of samples in the feature
     int _feat_ind; //!< Index of the feature
@@ -40,12 +54,7 @@ public:
      */
     Node(int feat_ind, int n_samp);
 
-    /**
-     * @brief Copy constructor
-     *
-     * @param o Node to be copied
-     */
-    Node(const Node &o);
+    virtual ~Node();
 
     /**
      * @brief Reindex the feature
@@ -122,18 +131,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     virtual void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot) = 0;
-
-    /**
-     * @brief Serialization function to send over MPI
-     *
-     * @param ar Archive representation of node
-     */
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        ar & _n_samp;
-        ar & _feat_ind;
-    }
 };
 
 typedef std::shared_ptr<Node> node_ptr;
diff --git a/src/feature_creation/node/operator_nodes/OperatorNode.cpp b/src/feature_creation/node/operator_nodes/OperatorNode.cpp
index 0a9f7cb7..5ed3cedd 100644
--- a/src/feature_creation/node/operator_nodes/OperatorNode.cpp
+++ b/src/feature_creation/node/operator_nodes/OperatorNode.cpp
@@ -6,16 +6,10 @@ OperatorNode::OperatorNode()
 OperatorNode::OperatorNode(std::vector<node_ptr> feats, int rung, int feat_ind) :
     Node(feat_ind, feats[0]->n_samp()),
     _feats(feats)
-{
-    _feats.reserve(_feats.size());
-}
+{}
 
-OperatorNode::OperatorNode(const OperatorNode &o) :
-    Node(o),
-    _feats(o._feats)
-{
-    _feats.reserve(_feats.size());
-}
+OperatorNode::~OperatorNode()
+{}
 
 double* OperatorNode::value_ptr(int offset)
 {
diff --git a/src/feature_creation/node/operator_nodes/OperatorNode.hpp b/src/feature_creation/node/operator_nodes/OperatorNode.hpp
index 79390ecd..96807771 100644
--- a/src/feature_creation/node/operator_nodes/OperatorNode.hpp
+++ b/src/feature_creation/node/operator_nodes/OperatorNode.hpp
@@ -9,6 +9,7 @@
 #include <boost/serialization/shared_ptr.hpp>
 #include <boost/serialization/split_member.hpp>
 #include <boost/serialization/array.hpp>
+#include <boost/serialization/vector.hpp>
 
 
 /**
@@ -19,6 +20,13 @@
 class OperatorNode: public Node
 {
     friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<Node>(*this);
+        ar & _feats;
+    }
 protected:
     std::vector<node_ptr> _feats;
 
@@ -38,11 +46,8 @@ public:
      * @param feat_ind index of the feature
      */
     OperatorNode(std::vector<node_ptr> feats, int rung, int feat_ind);
-    /**
-     * @brief Base Constructor
-     * @details This is only used for serialization
-     */
-    OperatorNode(const OperatorNode &o);
+
+    virtual ~OperatorNode();
 
     virtual std::string expr() = 0;
 
@@ -50,13 +55,6 @@ public:
 
     virtual void set_value(int offset = -1) = 0;
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        ar & boost::serialization::base_object<Node>(*this);
-        ar & _feats;
-    }
-
     /**
      * @brief Get the pointer to the feature's data
      * @details If the feature is not already stored in memory, then calculate the feature and return the pointer to the data
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_difference.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_difference.hpp
index 26477c60..a477568d 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_difference.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_difference.hpp
@@ -5,6 +5,13 @@
 
 class AbsDiffNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     AbsDiffNode();
@@ -51,12 +58,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_value.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_value.hpp
index ae3221f4..b70ec882 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_value.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/absolute_value.hpp
@@ -5,7 +5,13 @@
 
 class AbsNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     AbsNode();
 
@@ -51,12 +57,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/add.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/add.hpp
index a11e280f..2d12cb0d 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/add.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/add.hpp
@@ -5,7 +5,13 @@
 
 class AddNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     AddNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cos.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cos.hpp
index ceca1724..e69cb5b8 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cos.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cos.hpp
@@ -5,7 +5,13 @@
 
 class CosNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     CosNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube.hpp
index b7e9ca7d..8d8db3ab 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube.hpp
@@ -5,7 +5,13 @@
 
 class CbNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     CbNode();
 
@@ -51,13 +57,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube_root.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube_root.hpp
index 2d723daf..1522e3c8 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube_root.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/cube_root.hpp
@@ -5,7 +5,13 @@
 
 class CbrtNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     CbrtNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/divide.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/divide.hpp
index a98ad475..bdc5d628 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/divide.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/divide.hpp
@@ -5,7 +5,13 @@
 
 class DivNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     DivNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/exponential.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/exponential.hpp
index 5ed79cbc..d061b920 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/exponential.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/exponential.hpp
@@ -5,7 +5,13 @@
 
 class ExpNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     ExpNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/inverse.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/inverse.hpp
index 46c088a3..50a51274 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/inverse.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/inverse.hpp
@@ -5,6 +5,13 @@
 
 class InvNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     InvNode();
@@ -52,11 +59,5 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/log.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/log.hpp
index 00d6fa1e..fdae1b18 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/log.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/log.hpp
@@ -5,7 +5,13 @@
 
 class LogNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     LogNode();
 
@@ -51,13 +57,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/multiply.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/multiply.hpp
index b29516e6..070ffe2b 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/multiply.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/multiply.hpp
@@ -5,6 +5,13 @@
 
 class MultNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     MultNode();
@@ -52,12 +59,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/negative_exponential.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/negative_exponential.hpp
index e08b206b..515dc531 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/negative_exponential.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/negative_exponential.hpp
@@ -5,6 +5,13 @@
 
 class NegExpNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     NegExpNode();
@@ -52,12 +59,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sin.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sin.hpp
index db423ac2..5b31a635 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sin.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sin.hpp
@@ -5,6 +5,13 @@
 
 class SinNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     SinNode();
@@ -52,12 +59,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sixth_power.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sixth_power.hpp
index 57e47160..8e90b007 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sixth_power.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/sixth_power.hpp
@@ -5,6 +5,13 @@
 
 class SixPowNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     SixPowNode();
@@ -52,12 +59,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square.hpp
index 669e69b4..0e8c377c 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square.hpp
@@ -5,7 +5,13 @@
 
 class SqNode: public OperatorNode
 {
+    friend class boost::serialization::access;
 
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 public:
     SqNode();
 
@@ -52,12 +58,6 @@ public:
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
 
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square_root.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square_root.hpp
index e1f33e68..0986c332 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square_root.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/square_root.hpp
@@ -5,6 +5,13 @@
 
 class SqrtNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     SqrtNode();
@@ -51,13 +58,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
diff --git a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/subtract.hpp b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/subtract.hpp
index c8b167d2..71e0085f 100644
--- a/src/feature_creation/node/operator_nodes/allowed_operator_nodes/subtract.hpp
+++ b/src/feature_creation/node/operator_nodes/allowed_operator_nodes/subtract.hpp
@@ -5,6 +5,13 @@
 
 class SubNode: public OperatorNode
 {
+    friend class boost::serialization::access;
+
+    template <typename Archive>
+    void serialize(Archive& ar, const unsigned int version)
+    {
+        ar & boost::serialization::base_object<OperatorNode>(*this);
+    }
 
 public:
     SubNode();
@@ -51,13 +58,6 @@ public:
      * @param expected_abs_tot The expected absolute sum of all values in div_mult_leaves
      */
     void update_div_mult_leaves(std::map<std::string, double>& div_mult_leaves, double fact, double& expected_abs_tot);
-
-    template <typename Archive>
-    void serialize(Archive& ar, const unsigned int version)
-    {
-        // ar.template register_type<OperatorNode>();
-        ar & boost::serialization::base_object<OperatorNode>(*this);
-    }
 };
 
 #endif
\ No newline at end of file
-- 
GitLab