zenna
zenna

Reputation: 9176

How to cast to a variable type - emulating type variables in C++

I am implementing something similar to a typed genetic programming and have become a little stuck with regards to C++ types.

I have a network of nodes, nodes have different types, for example some are functional nodes whereas others are just data. In order to deal with collections of such nodes, I saw no option other than to use polymoprphism to store colection of base class pointers.

class Node {
private:
    std::string label;
    std::string node_type;
};

template
<typename FNC>
class FunctionalNode : public Node {
    std::function<FNC> function;
};

class Network {
   std::vector<Node*> nodes;
   ...
}

Note I have a templated FunctionalNode, which stores a std::function, I think (but am not certain) that my problem applies equally if I were to store a plain function pointer instead.

So the problem is, at some point given a Node pointer to a dervied FunctionalNode, I need to apply the stored function to some values. This means I need to cast the base pointer onto the derived class, but since it is templated I am not sure how to do this.

I would like to do something like the following fake C++ code, which would need something like type variables:

Node * applyfunction(Node * functional_node, std::vector<Node*> arguments) {
    typevariable function_type = convert_node_type_to_typevariable(functional_node.node_type)
    functional_node_derived * = static_cast<function_type>(functional_node);
    ....
}

Where a node's node_type is some structure I use to contain the type information of the node, e.g. the type of its functional form, and convert_node_type_to_typevariable would convert this to a typevariable I can use in this hypothetical C++ language.

Any ideas how I could implementing this seing as C++ lacks support for type variables, or a completely different approach to the problem?

Upvotes: 1

Views: 167

Answers (1)

jxh
jxh

Reputation: 70372

You should exploit your polymorphic structure. You can define Node with a pure virtual method instead of making applyfunction a free function.

class Node {
protected:
    std::string label;
    std::string node_type;
public:
    virtual ~Node () {}
    virtual Node * applyfunction (std::vector<Node *> args) = 0;
};

Then your derivations would perform the work.

template
<typename FNC>
class FunctionalNode : public Node {
    std::function<FNC> function;
public:
    Node * applyfunction (std::vector<Node *> args) {
        //...
    }
};

Upvotes: 2

Related Questions