www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Going from TypeInfo of template to TypeInfo of template parameter/member

reply Bill Baxter <dnewsgroup billbaxter.com> writes:
I'm trying to get info about types from their TypeInfo.

Say I have a struct like

struct Container(T)
{
    T[] elems;
}

And I have a TypeInfo for a Container!(float).  Is there any way to get 
the TypeInfo for a float out of that?  Or a double, or int, or whatever 
it happens to be.

TypeInfo get_container_element_type(TypeInfo container_typeinfo)
{
    ???
}

The TypeInfo's .next and .offTi are both null, so that's no help.
The toString includes the stringized version of the type "float", 
though, so I could try to use that.  Seems unreliable though.

Thanks for any suggestions.
--bb
Nov 12 2007
next sibling parent reply Christopher Wright <dhasenan gmail.com> writes:
Bill Baxter wrote:
 I'm trying to get info about types from their TypeInfo.
 
 Say I have a struct like
 
 struct Container(T)
 {
    T[] elems;
 }
 
 And I have a TypeInfo for a Container!(float).  Is there any way to get 
 the TypeInfo for a float out of that?  Or a double, or int, or whatever 
 it happens to be.
 
 TypeInfo get_container_element_type(TypeInfo container_typeinfo)
 {
    ???
 }
 
 The TypeInfo's .next and .offTi are both null, so that's no help.
 The toString includes the stringized version of the type "float", 
 though, so I could try to use that.  Seems unreliable though.
 
 Thanks for any suggestions.
 --bb

Looks like everyone's doing the same things these days :) My post a bit above yours is asking essentially the same question for classes and interfaces, so I'd guess there's no way to do that at compile time, and therefore probably no way to do that at runtime, in the general case. If you only need it at runtime, you could do something like: struct Container(T) { static TypeInfo containedType = typeid(T); //... } That assumes you're only dealing with code that you wrote.
Nov 12 2007
parent Bill Baxter <dnewsgroup billbaxter.com> writes:
Christopher Wright wrote:
 Bill Baxter wrote:
 I'm trying to get info about types from their TypeInfo.

 Say I have a struct like

 struct Container(T)
 {
    T[] elems;
 }

 And I have a TypeInfo for a Container!(float).  Is there any way to 
 get the TypeInfo for a float out of that?  Or a double, or int, or 
 whatever it happens to be.

 TypeInfo get_container_element_type(TypeInfo container_typeinfo)
 {
    ???
 }

 The TypeInfo's .next and .offTi are both null, so that's no help.
 The toString includes the stringized version of the type "float", 
 though, so I could try to use that.  Seems unreliable though.

 Thanks for any suggestions.
 --bb

Looks like everyone's doing the same things these days :) My post a bit above yours is asking essentially the same question for classes and interfaces, so I'd guess there's no way to do that at compile time, and therefore probably no way to do that at runtime, in the general case.

I'm not seeing the one you're talking about. You mean the one that was answered by using if(is(x==interface)) ?
 If you only need it at runtime, you could do something like:
 
 struct Container(T) {
    static TypeInfo containedType = typeid(T);
    //...
 }
 
 That assumes you're only dealing with code that you wrote.

It is code I wrote, but that won't help because all I have is the TypeInfo of the Container!(T). I don't have an instance of a Container!(T). But I think I found a way to do what i want in the other post. --bb
Nov 12 2007
prev sibling parent reply Kirk McDonald <kirklin.mcdonald gmail.com> writes:
Bill Baxter wrote:
 I'm trying to get info about types from their TypeInfo.
 
 Say I have a struct like
 
 struct Container(T)
 {
    T[] elems;
 }
 
 And I have a TypeInfo for a Container!(float).  Is there any way to get 
 the TypeInfo for a float out of that?  Or a double, or int, or whatever 
 it happens to be.
 
 TypeInfo get_container_element_type(TypeInfo container_typeinfo)
 {
    ???
 }
 
 The TypeInfo's .next and .offTi are both null, so that's no help.
 The toString includes the stringized version of the type "float", 
 though, so I could try to use that.  Seems unreliable though.
 
 Thanks for any suggestions.
 --bb

Not in the general case. However, you can easily add something like this: struct Container(T) { alias T value_type; T[] elems; } Thus, Container!(float).value_type will be float. -- Kirk McDonald http://kirkmcdonald.blogspot.com Pyd: Connecting D and Python http://pyd.dsource.org
Nov 12 2007
parent reply Bill Baxter <dnewsgroup billbaxter.com> writes:
Kirk McDonald wrote:
 Bill Baxter wrote:
 I'm trying to get info about types from their TypeInfo.

 Say I have a struct like

 struct Container(T)
 {
    T[] elems;
 }

 And I have a TypeInfo for a Container!(float).  Is there any way to 
 get the TypeInfo for a float out of that?  Or a double, or int, or 
 whatever it happens to be.

 TypeInfo get_container_element_type(TypeInfo container_typeinfo)
 {
    ???
 }

 The TypeInfo's .next and .offTi are both null, so that's no help.
 The toString includes the stringized version of the type "float", 
 though, so I could try to use that.  Seems unreliable though.

 Thanks for any suggestions.
 --bb

Not in the general case. However, you can easily add something like this: struct Container(T) { alias T value_type; T[] elems; } Thus, Container!(float).value_type will be float.

But all I have is the TypeInfo for the Container!(float). I'm trying to go from runtime TypeInfo's to concrete types via big if-else constructs. Like so: void do_stuff(TypeInfo it) { if (it == typeid(float)) { do_something_concrete!(float)(); } else if (it == typeid(float)) { do_something_concrete!(float)(); } else if (it is some instantiation of Container!(T)) { if (typeinfo of container's value_type == typeid(float)) { do_something_concrete!(Container!(float))(); } else if (...) ... } } But anyway, in writing this out I just realized that I can just test against typeinfo of instances of the container like else if (it = typeid(Container!(float)) {... } else if (it = typeid(Container!(int)) {... } I was just hoping to reuse the code for "match TypeInfo to basic type". Maybe there's still a way though. I could do something like template ident(T) { alias T ident; } bool match_element_type(alias C)(TypeInfo it) { if ( it == typeid(C!(float)) ) { do_something_concrete!(C!(float))(); return true; } ... return false; } ... //try to match basic types do { if (match_element_type(ident)(it)) break; if (match_element_type(Container)(it)) break; ... } Seems like that should work. --bb
Nov 12 2007
parent Bill Baxter <dnewsgroup billbaxter.com> writes:
Bill Baxter wrote:
 Kirk McDonald wrote:
 Bill Baxter wrote:
 I'm trying to get info about types from their TypeInfo.

 Say I have a struct like

 struct Container(T)
 {
    T[] elems;
 }

 And I have a TypeInfo for a Container!(float).  Is there any way to 
 get the TypeInfo for a float out of that?  Or a double, or int, or 
 whatever it happens to be.

 TypeInfo get_container_element_type(TypeInfo container_typeinfo)
 {
    ???
 }

 The TypeInfo's .next and .offTi are both null, so that's no help.
 The toString includes the stringized version of the type "float", 
 though, so I could try to use that.  Seems unreliable though.

 Thanks for any suggestions.
 --bb

Not in the general case. However, you can easily add something like this: struct Container(T) { alias T value_type; T[] elems; } Thus, Container!(float).value_type will be float.

But all I have is the TypeInfo for the Container!(float). I'm trying to go from runtime TypeInfo's to concrete types via big if-else constructs. Like so: void do_stuff(TypeInfo it) { if (it == typeid(float)) { do_something_concrete!(float)(); } else if (it == typeid(float)) { do_something_concrete!(float)(); } else if (it is some instantiation of Container!(T)) { if (typeinfo of container's value_type == typeid(float)) { do_something_concrete!(Container!(float))(); } else if (...) ... } } But anyway, in writing this out I just realized that I can just test against typeinfo of instances of the container like else if (it = typeid(Container!(float)) {... } else if (it = typeid(Container!(int)) {... } I was just hoping to reuse the code for "match TypeInfo to basic type". Maybe there's still a way though. I could do something like template ident(T) { alias T ident; } bool match_element_type(alias C)(TypeInfo it) { if ( it == typeid(C!(float)) ) { do_something_concrete!(C!(float))(); return true; } ... return false; } ... //try to match basic types do { if (match_element_type(ident)(it)) break; if (match_element_type(Container)(it)) break; ... } Seems like that should work.

Update: it did seem like it was going to work at first, but after a point I started getting Optlink crashes. It started popping up this pretty little MsgBox: --------------------------- Unexpected OPTLINK Termination at EIP=0044C37B --------------------------- EAX=01BA1318 EBX=00470800 ECX=00463EE0 EDX=00001001 ESI=012B4000 EDI=0046C72C EBP=0013FFF0 ESP=0013FF90 First=00430000 --------------------------- OK --------------------------- --bb
Nov 13 2007