I'm trying to make a list of template classes of variable types. So the idea is to loop of a list of objects that all have a common function, e.g. getValue, but a different type. The type could be any type, raw types or objects.
I need this because i want to have a class that has a list of attributes of different types that i want to be able to construct at runtime.
So my class would look something like:
class MyClass {
std::list<Attribute<?>*> attributes;
};
And my attribute template:
template<typename T>
class Attribute {
public:
Test(const T &t) : _t(t) {}
T getValue() const { return _t; }
void setValue(const T &t) { _t = t; }
private:
T _t;
};
int main() {
MyClass myClass;
myClass.attributes.push_back(new Attribute<int>(42));
myClass.attributes.push_back(new Attribute<double>(42.0));
}
As you can see the list of MyClass i put ? because that is my problem. I dont know how to make a list that will take different types of my Attribute template, i.e. int, double etc.
std::list<Attribute<?> *> attributes;
In Java, generics can be used for that. Is it possible in C++ to do this with somekind of construction? I tried using variadic templates but that doesnt seem to help solving my problem.
I need this but not in Java, in C++:
public class GenericAttribute<T> {
private T value;
public GenericAttribute (T value) {
setValue(value);
}
public T getValue() {
return value;
}
public void setValue(T value) {
this.value = value;
}
}
public static void main(String[] args) {
class Custom {
public Custom() {}
@Override public String toString() {
return "My custom object";
}
}
List<GenericAttribute<?>> attributes = new ArrayList<GenericAttribute<?>>();
attributes.add(new GenericAttribute<Integer>(1));
attributes.add(new GenericAttribute<Double>(3.1415926535));
attributes.add(new GenericAttribute<Custom>(new Custom()));
for (GenericAttribute<?> attr : attributes) {
System.out.println(attr.getValue());
}
}
Output:
1
3.1415926535
My custom object
Thanks for the help!
Test<int>
andTest<double>
are distinct types and as different asint
anddouble
. You need to either give them a common base, or apply some sort of type erasure. – Heavyarmedvoid*
as template argument – UniongetValue
functions with differing return types because you don't know the return type. The fact that you can't store these types is just a hint of a bigger problem. – Dismissboost::variadic
orboost::any
or a type-erased interface. – Dismiss