C++按返回类型选择函数

问题描述:

我意识到标准C++只能通过参数类型选择函数,而不是返回类型。即我可以这样做:C++按返回类型选择函数

void func(int); 
void func(double); 

但不

double func(); 
int func(); 

凡在前者,很明显,在后者,它是ambigious。是否有任何扩展让我告诉C++通过返回类型选择使用哪个函数?

谢谢!

+0

不是http://*.com/questions/ 226144/puzzle-overload-ac-function-according-the-the-return-value问同样的问题? – jjxtra 2010-04-26 23:06:21

+0

http://*.com/questions/1927587/methods-overriding-and-overloading – 2010-04-26 23:10:51

在同一个作用域中不能有两个函数具有相同的名称和签名(即参数类型)。通过使f()回报与重载转换运算符代理

int x=f(); 
double x=f(); // different behaviour from above 

:然而,你可以创建一个函数,将不同的表现取决于什么变量分配的结果,象这样

struct Proxy 
{ 
    operator double() const { return 1.1; } 
    operator int() const { return 2; } 
}; 

Proxy f() 
{ 
    return Proxy(); 
} 

参见http://ideone.com/ehUM1

这并不是说此特定的用例(返回不同数量的)是有用的,但也有 对于这个成语用途。

如果你有这两个功能,其中之一应该编译器挑,如果你简单地称为:

func(); 

你可以得到你所要求的是使用专门的函数模板最接近(注这you want to be very careful when specializing function templates):

template <typename ReturnT> 
ReturnT func(); 

template <> 
double func<>() { return 42; } 

template <> 
int func<>() { return 0; } 

然后就可以调用它,如下所示:

func<int>(); 
func<double>(); 
+1

我也同意你的看法,但应该可以在你调用int i = func()的情况下实现, ;'并且只在没有'void'函数时给出一个错误,并且'func()'在没有附带赋值的情况下被调用。虽然我不喜欢那样。 – 2010-04-26 23:03:44

因为编译器不知道你调用了哪个函数!

+0

不好的编译器,不能找出收集结果的变量的类型... – 2013-08-27 15:21:43

+0

@JoanCharmant:在你看来,编译器应该做什么,当它看到'auto result = func();'?结果是什么类型?该类型是否可以明确确定? – IInspectable 2016-12-11 14:57:25

否;实际上也很难实现。我依稀记得听说这是一个P-NP问题。

没有我所知道的。您最好以不同的方式命名函数,或者使用不同的参数让编译器(而不是您)区分它们。

另外,这样做:

struct myReturnType { 
    int myInt; 
    double myDouble; 
}; 

myReturnType func() { 
    ... 
} 

为什么不只是他们的名字不同?如果他们回复不同的事情,这听起来像他们可能不同的事情。为什么混淆你的代码?

+0

你是否同意返回类型在函数重载中不太重要? – Raindrop7 2016-12-09 00:52:48

+0

我认为重要的是以任何形式返回最适合该方法的数据(即,如果它是数值,则适当的精度)。如果您的方法正在计算某个值到最接近的整数,则返回它,并使用static_cast声明您很乐意转换为另一种类型,如果这是您在调用代码中需要的。 – 2016-12-09 11:02:35

+0

如果你的方法正在计算一些精确到浮点数的东西,然后返回它,这取决于调用者决定如何正确处理小数部分(舍入,地板,天花板等)。至少在你作为一个调用者的幻想中,你不会因为一种方法而得到什么...... – 2016-12-09 11:07:38

C++中有一个上下文,其中重载解析的结果取决于表达式左侧的“返回类型”。它是函数指针值与函数地址的初始化/赋值。它使用左侧大小的显式对象以及由显式类型转换创建的临时对象。

在你的情况下,它可以用来从两个重载的函数中选择一个特定的函数。例如:

int (*pfunc)() = func; // selects `int func()` 
int i = pfunc(); // calls `int func()` 

您可以使用此方法来迫使一个线路的过载的分辨率,虽然它看上去并不是很优雅

int i = ((int (*)()) func)(); // selects and calls `int func()` 

同样,在你手动执行重载这种情况。 C++没有任何特性会导致基于返回类型的隐式重载解析(除了我上面所说的)。

+0

这正是我所寻找的。谢谢! – 2016-12-09 00:18:32

这有点危险,但你可以创建你想要返回的不同类型的联合,并将这两个联合成一个返回联合的函数。例如:

typedef union { 
    double d; 
    int i; 
} my_union; 

my_union func(); 

然而,这将需要的功能和来电者以某种方式知道什么数据类型期望的结果,并可能导致各种错误。你可以做到这一点,但我绝对不会推荐它。

函数重载需要每个表单的不同签名,不包括返回类型。两种或多种形式是正确的,如果只是和他们在列表参数的数量或至少一种类型或参数的顺序不同,例如:

void print(); // 1 
void print(int, char); // 2 ok number of parameters 
void print(char, int); // 3 ok the order of parameters type 
int print(int, char); // 4 no the same signature as 2 except the return type