

下記のソースコードでどのようにすれば `S` で `D::T` が使えるようになりますでしょうか？

[code]

    template<typename Derived>
    struct S {
        using I = typename Derived::T;
    };
    
    struct D : S<D> {
        using T = int;
    };
    
    int main()
    {
        D d;
        return 0;
    }
    
[/code]


CC BY-SA 4.0
2023-02-24T13:17:12.663
93982
2023-02-25T05:54:02.767
2023-02-25T05:54:02.767
3060
57257
question
c++ templates
CRTPで依存関係のある型を使いたいですが、コンパイルエラーになります。


<https://stackoverflow.com/questions/47606667/how-to-get-typename-defined-in-
derived-from-base-class>  
上記リンクを参考にしていい感じになりそうだったので共有します。  
何が起こっているのか有識者の方教えていただけると幸いです。

[code]

    template <class T>
    struct traits;
    
    template <class Derived>
    struct Base {
      typedef typename traits<Derived>::T T;
    };
    
    template <typename T_>
    struct Impl : public Base<Impl<T_>> {
      typedef T_ T;
    };
    
    template <typename T_>
    struct traits<Impl<T_>> {
      typedef T_ T;
    };
    
    
    using SpecialImpl = Impl<int>;
    
    int main(){
        SpecialImpl si;
        
    }
    
[/code]


CC BY-SA 4.0
2023-02-24T14:01:52.943
93986
2023-02-24T14:08:57.477
2023-02-24T14:08:57.477
57257
57257
93982
answer


まず基本的な規則としてテンプレート中に現れる依存名 (テンプレート引数に依存する名前)
の解決はテンプレート引数が与えられるまで遅延されるというものがあります。 いわゆる Two phase name lookup です。

例えば以下のようなコードがあった場合、

[code]

    template<class T>
    struct foo {
        T::type a;
    };
    
    struct bar {
        using type = int;
    };
    
    int main(void) {
        foo<bar> baz;
    }
    
[/code]

`T` が決まらないと `T::type` が何者なのかわからないということはわかりますね。 これが依存名です。

また、クラステンプレートの暗黙の実体化は具体的な型が要求される文脈で起こることになっています。 この例では `baz` の宣言の時点がそうです。

* * *

では質問の例に当てはめてみると具体的な型が要求される文脈というのは `D` の基底として表れる `S<D>` ですが……この時点では `D`
はまだ定義が完了していないので `D::T` というメンバを持っていることがわかりません。

`D` がクラスであることはわかっているが中身がわかっていないという、いわゆる「不完全型」の状態です。 中身がわからないクラスから `T`
を探そうとしたためにエラーになっています。 エラーメッセージ中に不完全型 (incomplete type) という言葉が含まれていませんか？

* * *

逆に解決例のほうでは Two phase name lookup の手順の中で解決できない名前というものが出てこない (不完全型が現れない)
ので上手くいっているといえます。


CC BY-SA 4.0
2023-02-24T23:57:18.027
93990
2023-02-24T23:57:18.027
3364
93982
answer