CRTP:如何推断要用作返回类型的成员类型?

CRTP: How to infer type of member to be used as return type?

本文关键字:成员 成员类 类型 返回类型 何推断 CRTP      更新时间:2023-10-16

我想使 CRTP 基方法的返回类型取决于派生中成员的类型,例如:

template <typename C>
struct sum_a_b {
??? sum() { return static_cast<C*>(this)->a + static_cast<C*>(this)->b; }
}
template <typename T> struct a_b : sum_a_b<a_b<T>> { T a,b; };

我应该用什么代替???

我尝试了不同的方法来声明返回类型:

template <typename T>
struct base {
int get_ok() {  
return static_cast<T*>(this)->value; 
}
auto get_invalid() -> decltype(static_cast<T*>(this)->value) {
return static_cast<T*>(this)->value; 
}
typename T::value_type get_incomplete_type_foo() {  
return static_cast<T*>(this)->value; 
}
auto get_incomplete_type_again() -> decltype(T().value) {  
return static_cast<T*>(this)->value; 
}
};
struct foo : base<foo> {
typedef int value_type;
value_type value;
};

编译的唯一方法是int get_ok,对于其他方法,我得到(对于get_invalid_cast(:

invalid static_cast from type 'base<foo>*' to type 'foo*'
auto get_invalid() -> decltype(static_cast<T*>(this)->value) {  return static_cast<T*>(this)->value; }
^

或(其他两个(

invalid use of incomplete type 'struct foo'
typename T::value_type get_incomplete_type_foo() {  return static_cast<T*>(this)->value; }
^

我认为在 c++14 之前唯一可用的解决方法是使用类型特征:

#include <iostream>
template<typename T>
struct Value;
template <typename T>
struct Base
{
typename Value<T>::type get_value(void)
{  
return static_cast<T*>(this)->m_value; 
}
};
struct Derived;
template<> 
struct Value<Derived>
{
using type = float;
};
struct Derived: public Base<Derived>
{
Value<Derived>::type m_value{};
};
int main()
{
Derived derived{};
std::cout << derived.get_value() << std::endl;
}

在线编译器

如果Derived类型是模板,则类型特征专用化将如下所示:

template<typename U>
struct Derived;
template<typename U> 
struct Value<Derived<U>>
{
using type = float;
};