【发布时间】:2020-12-17 20:14:43
【问题描述】:
我想使用 SFINAE 创建一个模板化成员函数,该函数采用 Consumer 函子。某物是否是消费者取决于模板化的static constexpr bool isConsumer 成员变量。我已将代码简化为以下示例:
#include <type_traits>
template <typename T>
struct Container {
T data[100];
template <typename Consumer>
static constexpr bool isConsumer = std::is_invocable_r_v<void, Consumer, T>;
template <typename Consumer, std::enable_if_t<isConsumer<Consumer>, int> = 0>
void forEach(const Consumer &consumer);
};
template <typename T>
template <typename Consumer, std::enable_if_t<Container<T>::template isConsumer<Consumer>, int>>
void Container<T>::forEach(const Consumer &consumer)
{
for (int i = 0; i < 100; ++i) {
consumer(data[i]);
}
}
由于我不理解的原因,这无法编译:
<source>:16:20: error: out-of-line definition of 'forEach' does not match any declaration in 'Container<T>'
void Container<T>::forEach(const Consumer &consumer)
^~~~~~~
当我内联isConsumer 时,它确实编译得很好,例如直接使用std::is_invocable_r_v。我想避免这种情况,因为在我的真实代码中,Consumer 的签名非常复杂,这需要大量的复制/粘贴。
将isConsumer 拉到类之外也不是一种选择,因为在我的真实代码中,它依赖于Container 中的私有类型定义。它必须在类内。
如何在这里正确使用std::enable_if?
【问题讨论】:
标签: c++ templates c++17 sfinae enable-if