In C++, I can instantiate a generic type at compile time and then construct it at runtime:
struct Vertex {};
struct Edge {};
template<typename NodeType, typename IdType>
struct Wrapper {
IdType id;
Wrapper(IdType id) : id{id} {};
};
int main() {
using vertexWrapper = Wrapper<Vertex, int>;
vertexWrapper v(3);
}
The variables are clearly separated, and types never look/feel like values. I am trying to do something similar in Chapel:
record Vertex {}
record Edge {}
record Wrapper {
type nodeType;
type idType;
var id: idType;
proc init(id) {
this.id = id;
}
}
type vertexWrapper = Wrapper(Vertex, int);
var v1 = 3: vertexWrapper;
When I compile this code, I get:
chpl -o graph-add-inclusion --cc-warnings test.chpl
test.chpl:9: In initializer:
test.chpl:10: error: can't omit initialization of field "nodeType", no type or default value provided
test.chpl:10: error: can't omit initialization of field "idType", no type or default value provided
Is there a way to separate type construction from value construction in Chapel to achieve an effect of a tagged type as I am trying to get in my example? I use tagged types to have single implementation that's common for two kinds of entities (vertices and edges here), but I want these entities to be different types.
There is a further, related question. Should I be able to just write:
type vertexWrapper = Wrapper(Vertex);
and then have integer deduced separately from my constructor?
It seems that constructors are checked at definition time without the possibility that types can be provided separately from values. Did I get this right, and, if I did, is this something that will change in the future?