title: Get object's type from pointer to base class at runtime
body: <p>I'm working with a class library where all classes are, directly or indirectly, derived from a base class <code>Base</code> and have a name. The library provides a facility to search for objects by a name, which will return a <code>Base*</code>.</p>
  
  <p>Is there any way to find the type of the returned object without checking all possibilities using <code>dynamic_cast</code>s as I did in the following example? I'd like to avoid that, if at all possible, since the derived classes have template parameters, which makes for quite a few possibilities.</p>
  
  <p>It would also be fine if I were at least able to find out the class type (<code>T1</code> or <code>T2</code>, in the example below) without knowing the template type, ie. do something like a <code>dynamic_cast&lt;T1&lt;i_dont_care&gt;*&gt;</code>.</p>
  
  <pre><code>#include &lt;iostream&gt;
  
  using namespace std;
  
  class Base {
  public:
      virtual ~Base() {}
  };
  
  template &lt;typename T&gt; class T1 : public Base {};
  template &lt;typename T&gt; class T2 : public Base {};
  
  Base *find_by_name() {
      return new T2&lt;int&gt;();
  }
  
  int main() {
      Base *b = find_by_name();
  
      if (T1&lt;int&gt; *p = dynamic_cast&lt;T1&lt;int&gt;*&gt;(b)) {
          cout &lt;&lt; "T1&lt;int&gt;" &lt;&lt; endl;
          // do something meaningful with p
      } else if (T1&lt;double&gt; *p = dynamic_cast&lt;T1&lt;double&gt;*&gt;(b))
          cout &lt;&lt; "T1&lt;double&gt;" &lt;&lt; endl;
      else if (T2&lt;int&gt; *p = dynamic_cast&lt;T2&lt;int&gt;*&gt;(b))
          cout &lt;&lt; "T2&lt;int&gt;" &lt;&lt; endl;
      else if (T2&lt;double&gt; *p = dynamic_cast&lt;T2&lt;double&gt;*&gt;(b))
          cout &lt;&lt; "T2&lt;double&gt;" &lt;&lt; endl;
      else
          cout &lt;&lt; "unknown" &lt;&lt; endl;
  
      delete b;
  
      return 0;
  }
  </code></pre>
  
  <p>Note that the above example is simplified, ie. in each <code>if</code> I'd do something meaningful with <code>p</code>.</p>
  
  <p>I do realize that this is bad design from the very start, however I'm stuck with this library and there's also no way for me to change its implementation.</p>