12

我正在尝试做这样的事情(在 c++11 中):

#include <utility>

template <typename T>
struct base {
    using type = decltype( std::declval<T>().foo() );
};

struct bar : base<bar> {
    int foo() { return 42;}
};

int main() {
    bar::type x;
}

失败了

prog.cc: In instantiation of 'struct base<bar>':
prog.cc:8:14:   required from here
prog.cc:5:46: error: invalid use of incomplete type 'struct bar'
     using type = decltype( std::declval<T>().foo() );
                            ~~~~~~~~~~~~~~~~~~^~~
prog.cc:8:8: note: forward declaration of 'struct bar'
 struct bar : base<bar> {
        ^~~

如何为bar::fooin的返回类型声明别名base?不可能吗?

这个问题似乎是相当相关的:对于不完整类型的呼叫运算符的 decltype 的特殊行为,尽管我无法将那里给出的答案应用于我的案例。

4

1 回答 1

12

您可以制作type模板类型别名,以便用户可以在定义bar可用后对其进行实例化。这会将最终语法从 更改bar::typebar::type<>

template <typename T>
struct base {
    template <typename G = T>
    using type = decltype( std::declval<G>().foo() );
};

struct bar : base<bar> {
    int foo() { return 42;}
};

int main() {
    bar::type<> x;
}

godbolt.org 上的实时示例

于 2019-06-07T16:22:18.503 回答