【发布时间】:2019-01-01 21:08:54
【问题描述】:
在 C++11 中编写下面的static constexpr size_t Foo<>::sum() 方法最简洁的方法是什么?这适用于 C++17 编译器,但我正在寻找一种在 C++11 模式下适用于 g++、clang 和 Visual Studio 2015 的方法。
#include <iostream>
#include <type_traits>
template<typename T,size_t N>
class Foo
{
public:
static constexpr size_t sum();
};
template<typename>
struct is_foo : std::false_type { };
template<typename T,size_t N>
struct is_foo<Foo<T,N>> : std::true_type { };
template<typename T,size_t N>
constexpr size_t Foo<T,N>::sum()
{
if constexpr (is_foo<T>::value)
return N + T::sum();
else
return N;
}
int main()
{
constexpr size_t sum = Foo<Foo<Foo<double,3>,4>,5>::sum(); // 12 = 3+4+5
std::cout << "sum = " << sum << std::endl;
return 0;
}
编译运行:
$ g++ --version
g++ (GCC) 7.3.1 20180303 (Red Hat 7.3.1-5)
...
$ g++ -std=c++17 sum.cpp
$ ./a.out
sum = 12
我可以为sum() 编写一个外部函子来完成此任务,但我真的希望它是上面的static constexpr 成员函数。这在 C++11 中是否可行?
【问题讨论】:
-
你只是在问如何替换
if constexpr,对吧?enable_if? -
我尝试使用
constexpr typename std::enable_if<is_foo<T>::value,size_t>::type Foo<T,N>::sum()进行 SFINAE,但收到错误prototype for 'constexpr typename std::enable_if<is_foo< <template-parameter-1-1> >::value, long unsigned int>::type Foo<T, N>::sum()' does not match any in class 'Foo<T, N>'。
标签: c++ c++11 templates c++17 template-meta-programming