具有灵活返回类型的 C++ 函数模板

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4530756/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 15:39:55  来源:igfitidea点击:

C++ Function Template With Flexible Return Type

c++templates

提问by Ignatius Reza

Let's say that we have a function like so

假设我们有一个像这样的函数

template <class T, class T2>
T getMin(T a, T2 b) {
  if(a < b)
    return a;
  return b;
}

if we call the function like so

如果我们像这样调用函数

int a, b;
long c;

a = getMin(b, c);

if c is < a, then the value of c will be type casted to int.

如果 c < a,则 c 的值将被类型转换为 int。

Is it possible to make the return type flexible so that it would return an int, or long, or any other type considered smaller by "<" without being type casted?

是否可以使返回类型灵活,以便它返回 int、long 或任何其他被“<”认为较小的类型而不进行类型转换?

edit : the type involved in the function can be anything from simple type to complex classes where typecasting sometime won't be possible.

编辑:函数中涉及的类型可以是从简单类型到有时无法进行类型转换的复杂类的任何类型。

回答by peoro

C++0x will allow you to use the autokeyword in order to let the compiler derive the return time of an expression.

C++0x 将允许您使用auto关键字来让编译器导出表达式的返回时间。



For C++03 the only way I found to automatize such process is to define a template class Promotionthat defines the strongest type between two types, and then specialize it for any couple of types you might need to use.

对于 C++03,我发现自动化此类过程的唯一方法是定义一个模板类Promotion,该类定义两种类型之间的最强类型,然后将其专门用于您可能需要使用的任何类型。

template<> class Promotion< long, int > { typedef long strongest; }
template<> class Promotion< int, long > { typedef long strongest; }

and thus:

因此:

template< typename T1, typename T2 >
Promotion<T1,T2>::strongest function( const T1 &a, const T2 &b ) { ... }

If you choose to try this solution, I'd suggest to generate the Promotion specializations with an automatically generated header file.

如果您选择尝试此解决方案,我建议您使用自动生成的头文件生成促销专业化。



Edit: I reread the question after reading the other (now deleted) answer:

编辑:我在阅读另一个(现已删除)答案后重读了这个问题:

You can't return the type of the smaller variable. That's because the value of the variables will only be found out at runtime, while your function return type must be defined at compile time.

您不能返回较小变量的类型。那是因为变量的值只会在运行时被发现,而你的函数返回类型必须在编译时定义。

The solution I proposed will return always the strongest type between the two variables' type.

我提出的解决方案将始终返回两个变量类型之间最强的类型。

回答by Johannes Schaub - litb

As has been said, you want to take the type that is more generic. Like, intand doubleshould become double; char*and stringshould become string. This works with my promote<>template. Just write

如前所述,您希望采用更通用的类型。喜欢,int并且double应该成为doublechar*并且string应该成为string. 这适用于我的promote<>模板。写就好了

template <class T1, class T2>
typename promote<T1, T2>::type getMin(T1 const& a, T2 const& b) {
  if(a < b)
    return a;
  return b;
}

This will always return a copy, even if T1and T2is the same type (like string), which is why I would overload it for non-const same-type arguments

这将始终返回一个副本,即使T1T2是相同类型(如string),这就是为什么我会为非常量相同类型参数重载它

template <class T>
T &getMin(T &a, T &b) {
  if(a < b)
    return a;
  return b;
}

These two variants seem to be a reasonable configuration. If you want to have a slightly more risky, but in more cases performant, solution, you can accept T const&, also accepting temporaries. If you then use it like getMin(a + b, b + c), which could pass temporaries, and use the result directly, that's all fine. The result is usable and can still be copied into a local variable.

这两个变体似乎是一个合理的配置。如果你想要一个稍微有点风险但在更多情况下性能更好的解决方案,你可以接受T const&,也可以接受临时的。如果然后使用它 like getMin(a + b, b + c),它可以传递临时值,并直接使用结果,那一切都很好。结果是可用的,并且仍然可以复制到局部变量中。