在一个数字比较函数中,我们可以使用if子句,一个是if else使用,另一个是直接使用return。因为如果它没有返回大的那个,那么另一个肯定是更大的那个。
现在问题是:哪个更有效率?我测试时机功能无法区分。
方法A:
int getmax(int a,int b){
if (a>b)return a;
else return b;
}
方法B:
int getmax(int a,int b){
if (a>b)return a;
return b;
}
很抱歉让你们中的一些人不高兴。我有这个问题是因为我想知道else子句对时间的贡献。 else条款会花费更多时间吗?虽然我在for循环中运行了1亿次,但似乎是随机效率。
答案 0 :(得分:2)
如果进行这样的比较,我认为没有意义,但如果你真的好奇,让我们比较VC11生成的汇编:
int getmax_1(int a,int b)
{
if (a>b)
return a;
else
return b;
}
int getmax_2(int a,int b)
{
if (a>b)
return a;
return b;
}
<强> getmax_1 强>
if (a>b)
002017BE mov eax,dword ptr [a]
002017C1 cmp eax,dword ptr [b]
002017C4 jle getmax_1+2Dh (02017CDh)
return a;
002017C6 mov eax,dword ptr [a]
002017C9 jmp getmax_1+30h (02017D0h)
else
002017CB jmp getmax_1+30h (02017D0h)
return b;
002017CD mov eax,dword ptr [b]
<强> getmax_2 强>
if (a>b)
002017FE mov eax,dword ptr [a]
00201801 cmp eax,dword ptr [b]
00201804 jle getmax_2+2Bh (020180Bh)
return a;
00201806 mov eax,dword ptr [a]
00201809 jmp getmax_2+2Eh (020180Eh)
return b;
0020180B mov eax,dword ptr [b]
然而,这是一个Debug构建。在发布版本中,这两个调用肯定会内联,第二个函数中的附加调用可能会被删除。
所以...没有区别,真的。
答案 1 :(得分:0)
我强烈建议使用第二个选项,因为它基本上做同样的事情,但没有任何额外的代码。你可以这样看待它:
函数在return
语句处转义,并且可能返回指定的值。话虽如此,在if
语句之后逃避函数已经是一个好主意,并且没有任何问题。 return
之后的if
语句将退出该函数,之后不考虑任何代码。这意味着else
是不必要的,并且只是编译器的额外工作,而且没有必要。
答案 2 :(得分:0)
绝对没有区别。 else
子句不生成任何可执行代码。在机器指令级别,给定地址只有条件和无条件分支。在C中排序goto
所以你的两个函数都会这样执行:
if (a > b) goto label_1;
return_register = b;
goto label_2;
label_1:
return_register = a;
label_2:
return return_register;
答案 3 :(得分:0)
我看到它的方式,你已经问过一个或另一个在C或C ++领域是否有效 。 The C standard说:
在抽象机器中,所有表达式都按语义指定的方式进行计算。一个 实际实现不需要评估表达式的一部分,如果它可以推导出它 不使用值,不产生任何副作用(包括由...引起的任何副作用) 调用函数或访问volatile对象。)
C ++标准有类似之处。
由于我们缺少关于实际实施的关键细节(例如,一段代码是非最优的而另一条是否是最优的),并且标准没有指定效率>
em>,你的问题没有明确的答案......至少,在C或C ++领域 。您必须标记编译器的任何内容,而不是[c]和[c ++]。可能影响该计划效率的其他因素是......嗯......程序!众所周知,随着代码和数据的增长,缓存未命中的风险也随之增加。由于这个原因,你可能不应该自己测试这段代码:没有任何有意义的东西,因为这些数字会在你改变某些东西时改变。
出于这个原因,我们经常通过解决现实问题,易于阅读且易于编写代码来避免过早优化 。一旦您获得了解决实际问题的解决方案(以及您的老板对其进行优化的权限或请求),请使用 profiler 确定最重要的瓶颈,并尝试优化这些瓶颈。
如果您尝试在其他任何地方进行优化,特别是通过引入额外的代码或数据来减少其他地方的代码或数据,那么您可能会进一步推动更加重要的优化。
一旦您优化了最重要的瓶颈,再次使用您的探查器确保优化成功,并确定可以优化的其他区域。
有一天,这可能很好地挽救了你的工作......