1

再帰テンプレートを使用して、C++ で非常に単純な単一継承スタック トレースを実装しようとしています。

#include <iostream>
using namespace std;
template <class C> struct MakeAlias : C{ typedef C Base; };
class StackTrace{
      public:
      static int var;
      virtual ~StackTrace() {}
      template <class T> void printStackTrace(T* c){
          if(typeid(T)==typeid(StackTrace))return; 
          cout << typeid(T).name() << "." << endl;
          class T::Base *V;
          printStackTrace(V);
     }
};
class A : public MakeAlias<StackTrace>{
};
class B : public MakeAlias<A>{
};
class C : public MakeAlias<B>{
    public:
    void hello(){
        cout << "hello from ";
        StackTrace::printStackTrace(this);
        cout << endl;
    }

};
int main(){
    C c;
    c.hello();
}

すべて問題ないはずですが、コンパイルしようとすると、g++ は
if(typeid(T)==typeid(StackTrace))return;を無視します。次のエラーを返します。

st.cpp: In member function `void StackTrace::printStackTrace(T*) [with T = StackTrace]':
st.cpp:13:   instantiated from `void StackTrace::printStackTrace(T*) [with T = A]'
st.cpp:13:   instantiated from `void StackTrace::printStackTrace(T*) [with T = B]'
st.cpp:13:   instantiated from `void StackTrace::printStackTrace(T*) [with T = C]'
st.cpp:24:   instantiated from here
st.cpp:12: error: no type named `Base' in `class StackTrace'
st.cpp:13: error: no type named `Base' in `class StackTrace'

C::Base::Base::Base::Base /StackTrace::Base/ クラスを呼び出そうとしますが、実行時に呼び出されることはありません。printStackTrace 宣言の直後にreturn文を入れても同じエラーと評価されます。スコープとメンバー関数が動的にチェックされないのはなぜですか? また、コンパイラがreturnを無視するのはなぜですか?

4

2 に答える 2