Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/148.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 函数在预期为长时返回double_C++_C++14_Functor - Fatal编程技术网

C++ 函数在预期为长时返回double

C++ 函数在预期为长时返回double,c++,c++14,functor,C++,C++14,Functor,我最近回答了另一个问题,在我的回答中,我有以下代码 template<typename T, typename ... Ts> struct are_arithmetic{ enum { value = std::is_arithmetic<T>::value && are_arithmetic<Ts...>::value }; }; template<typename T> struct are_

我最近回答了另一个问题,在我的回答中,我有以下代码

template<typename T, typename ... Ts>
struct are_arithmetic{
    enum {
        value = std::is_arithmetic<T>::value && are_arithmetic<Ts...>::value
    };
};

template<typename T>
struct are_arithmetic<T>{
    enum {
        value = std::is_arithmetic<T>::value
    };
};

template<typename Arg, typename = std::enable_if_t<std::is_arithmetic<Arg>::value>>
Arg max(Arg arg){
    return arg;
}

template<typename Arg, typename Arg1, typename ... Args, typename = typename std::enable_if_t<are_arithmetic<Arg, Arg1, Args...>::value>>
auto max(Arg arg, Arg1 arg1, Args ... args){
    auto max_rest = max(arg1, args...);
    return arg > max_rest ? arg : max_rest;
}
他从stdout拿到了d l


这表明函数的返回类型与预期完全不同。为什么函数不返回long?

在我看来,当max函数被调用为:

auto res = max(1.0, 2, 3.0f, 5, 7l);
然后签字:

auto max(Arg arg, Arg1 arg1, Args ... args){
    auto max_rest = max(arg1, args...);
    return arg > max_rest ? arg : max_rest;
}
这里,Arg显然是一个双精度

然后返回值是一个三元运算符:

return 1.0 > max_rest ? 1.0 : max_rest;
max_rest到底是什么并不重要。让我们说这确实是一个漫长的过程。有一个三元运算符,有一个双表达式和一个长表达式

在我看来,长表达式的类型将被提升为double,因此返回自动类型是double。

的返回类型

template<typename Arg, typename Arg1, typename ... Args, typename = typename std::enable_if_t<are_arithmetic<Arg, Arg1, Args...>::value>>
auto max(Arg arg, Arg1 arg1, Args ... args){
    auto max_rest = max(arg1, args...);
    return arg > max_rest ? arg : max_rest;
}
不依赖于值,而是给定类型。
因此,这里它返回所有参数的公共类型。

如何规避此问题?定义“规避”。我不清楚你想解决什么问题。给定定义max的方式,最终结果将始终被类型提升为其参数中最宽的参数。这确实是正确的做法。这里,您的参数是double、int、float、int和long。整个max函数最终递归扩展为一个巨大的嵌套三值运算符。因此,您的结果将始终是其参数的最宽类型。如果要显式地将结果强制转换为long,那么如何知道实际的max不是分数双精度的呢?我的意思是,我如何定义这个函数,使得不会发生类型提升。我不需要使用三元运算符,这就是我第一次使用的方法。只有当max的所有参数都是常量时,这才可能。如果他们没有,这当然是不可能的。如果是,则可以使用专门化来解决问题。因此,您的max将读取如下内容:返回max_value::value,然后定义一个max_value模板类,使用两个不透明值作为模板参数,默认第三个参数为_less=value1template<typename Arg, typename Arg1, typename ... Args, typename = typename std::enable_if_t<are_arithmetic<Arg, Arg1, Args...>::value>> auto max(Arg arg, Arg1 arg1, Args ... args){ auto max_rest = max(arg1, args...); return arg > max_rest ? arg : max_rest; }