概念:需要一个类型的函数而不默认构造该类型
Concepts: require a function on a type without default constructing that type
我需要要求某个类型 A 存在一个函数 f(A, A::B).
我正在通过使用 A 和 A::B 的实例调用 f 来测试它。是否有一种不那么夸张的方法来测试依赖类型的实例而不需要默认可构造的?
template <class Container>
concept CanPutData = requires (Container a)
{
//put(typename Container::data_type{}, a); // overconstrained
put(*reinterpret_cast<typename Container::data_type*>(0), a); // oof
};
void test(CanPutData auto container) {}
template<class Container>
void put(typename Container::data_type const& data, Container& into) {}
template<class Data>
struct data_container { using data_type = Data; };
struct not_default_constructible_data { int& v; };
int main()
{
test(data_container<not_default_constructible_data>{});
return 0;
}
同样的方法你已经得到了一个 Container
而不需要它是默认可构造的:只需将它粘贴在 requires 表达式的参数列表中:
template <class Container>
concept CanPutData = requires (Container container, typename Container::data_type data)
{
put(data, container);
};
你也可以把Container::data_type
放在模板参数列表里
template <class Container, class DataType = Container::data_type>
concept CanPutData = requires (DataType d, Container a)
{
put(d, a);
};
这种形式的好处是当requires
-clause比较大时,如果Container
没有data_type
成员,编译器只会报模板参数列表不满足约束,rather than output the entire requires clause.
我需要要求某个类型 A 存在一个函数 f(A, A::B).
我正在通过使用 A 和 A::B 的实例调用 f 来测试它。是否有一种不那么夸张的方法来测试依赖类型的实例而不需要默认可构造的?
template <class Container>
concept CanPutData = requires (Container a)
{
//put(typename Container::data_type{}, a); // overconstrained
put(*reinterpret_cast<typename Container::data_type*>(0), a); // oof
};
void test(CanPutData auto container) {}
template<class Container>
void put(typename Container::data_type const& data, Container& into) {}
template<class Data>
struct data_container { using data_type = Data; };
struct not_default_constructible_data { int& v; };
int main()
{
test(data_container<not_default_constructible_data>{});
return 0;
}
同样的方法你已经得到了一个 Container
而不需要它是默认可构造的:只需将它粘贴在 requires 表达式的参数列表中:
template <class Container>
concept CanPutData = requires (Container container, typename Container::data_type data)
{
put(data, container);
};
你也可以把Container::data_type
放在模板参数列表里
template <class Container, class DataType = Container::data_type>
concept CanPutData = requires (DataType d, Container a)
{
put(d, a);
};
这种形式的好处是当requires
-clause比较大时,如果Container
没有data_type
成员,编译器只会报模板参数列表不满足约束,rather than output the entire requires clause.