C++ 为什么这个模板constexpr函数不';不能在gcc上编译,但在clang上运行良好?

C++ 为什么这个模板constexpr函数不';不能在gcc上编译,但在clang上运行良好?,c++,gcc,clang,c++14,C++,Gcc,Clang,C++14,正如您在这里看到的,这不会在gcc上编译,错误如下: prog.cc: In instantiation of 'constexpr B convert(A) [with A = unsigned char; B = short unsigned int]': prog.cc:16:52: required from here prog.cc:12:1: error: body of constexpr function 'constexpr B convert(A) [with A = u

正如您在这里看到的,这不会在gcc上编译,错误如下:

prog.cc: In instantiation of 'constexpr B convert(A) [with A = unsigned char; B = short unsigned int]':
prog.cc:16:52:   required from here
prog.cc:12:1: error: body of constexpr function 'constexpr B convert(A) [with A = unsigned char; B = short unsigned int]' not a return-statement
守则:

#include <stdint.h>
#include <limits>
#include <iostream>

template< typename A, typename B >
constexpr B convert( A a )
{
    auto aMax = std::numeric_limits< A >::max();
    auto bMax = std::numeric_limits< B >::max();

    return a * ( bMax / aMax );
}

int main()
{
    std::cout << convert< uint8_t, uint16_t >( 128 ) << std::endl;
    return 0;
}
#包括
#包括
#包括
模板
constexpr B转换(A)
{
自动aMax=std::numeric_limits::max();
自动bMax=std::数值限制::max();
返回a*(b最大值/最大值);
}
int main()
{

std::cout(128)此代码需要一个名为“放松constexpr函数上的约束”的C++14功能。从3.4版开始,它就在Clang中得到支持,但GCC随后会抱怨函数模板

不过,不需要C++14,只需将其重写为

template <typename B, typename A> //! Note that I reordered the parameters
constexpr B convert( A a )
{
    return a * (std::numeric_limits< B >::max() / std::numeric_limits< A >::max());
}
template/!注意,我对参数进行了重新排序
constexpr B转换(A)
{
返回a*(std::numeric_limits::max()/std::numeric_limits::max());
}
还可以使用别名声明

template <typename T, T v>
using iconst = std::integral_constant<T, v>;

template <typename B, typename A>
constexpr B convert( A a )
{
    using aMax = iconst<A, std::numeric_limits< A >::max()>;
    using bMax = iconst<B, std::numeric_limits< B >::max()>;
    return a * (bMax::value / aMax::value);
}
模板
使用iconst=std::integral_常量;
模板
constexpr B转换(A)
{

使用aMax=iconst

这段代码需要一个名为“放松constepr函数的约束”的C++14功能。从3.4版开始,Clang就支持它,但GCC随后会抱怨函数模板

不过,不需要C++14,只需将其重写为

template <typename B, typename A> //! Note that I reordered the parameters
constexpr B convert( A a )
{
    return a * (std::numeric_limits< B >::max() / std::numeric_limits< A >::max());
}
template/!注意,我对参数进行了重新排序
constexpr B转换(A)
{
返回a*(std::numeric_limits::max()/std::numeric_limits::max());
}
还可以使用别名声明

template <typename T, T v>
using iconst = std::integral_constant<T, v>;

template <typename B, typename A>
constexpr B convert( A a )
{
    using aMax = iconst<A, std::numeric_limits< A >::max()>;
    using bMax = iconst<B, std::numeric_limits< B >::max()>;
    return a * (bMax::value / aMax::value);
}
模板
使用iconst=std::integral_常量;
模板
constexpr B转换(A)
{
使用aMax=iconst