下面是我的伪代码。
function highest(i, j, k)
{
if(i > j && i > k)
{
return i;
}
else if (j > k)
{
return j;
}
else
{
return k;
}
}
我认为那会起作用,但在C++中这是最有效的方法吗?
下面是我的伪代码。
function highest(i, j, k)
{
if(i > j && i > k)
{
return i;
}
else if (j > k)
{
return j;
}
else
{
return k;
}
}
我认为那会起作用,但在C++中这是最有效的方法吗?
要找出最大值,你需要仅查看3个整数,不多不少。但是你正在使用6个整数和3次比较。你应该能够用3次或2次比较来完成。
int ret = max(i,j);
ret = max(ret, k);
return ret;
template <typename T> const T& max(const T& pA, const T& pB, const T& pC){ return max(pA, max(pB, pC)); }
。 - GManNickGmax(i, max(j, k))
可以简化为一行代码。我也喜欢模板版本。 - Nick Bedfordstd::max
,然后就完成了。@Chris:GNU STL将中位数定义为私有函数,也许这就是你想到的。 - Potatoswatter伪代码:
result = i
if j > result:
result = j
if k > result:
result = k
return result
cmov
这样的预测指令,编译器就很可能会使用它们。+1(但愿我能超越邪恶的max
并给予+10)。 - Norman Ramsey怎么样?
return i > j? (i > k? i: k): (j > k? j: k);
两个比较,不使用瞬态临时堆栈变量...
int ret = max(i,j);
ret = max(ret, k);
return ret;
http://ideone.com/hlnl7QZX(0.39秒)
由Ignacio Vazquez-Abrams提供的解决方案:
result = i;
if (j > result)
result = j;
if (k > result)
result = k;
return result;
http://ideone.com/JKbtkgXi (0.40秒)
还有Charles Bretana的:
return i > j? (i > k? i: k): (j > k? j: k);
http://ideone.com/kyl0SpUZ (0.40秒)
在这些测试中,所有解决方案的执行时间相差不到3%。你试图优化的代码已经非常简短了。即使你能将其中的一条指令压缩掉,它也很难对整个程序产生巨大影响(现代编译器可能会捕捉到这个小优化)。请把时间花在其他地方。
编辑:更新了测试,结果发现之前它仍然优化了部分内容。希望现在不再优化。
result = i;
if (j > result)
result = j;
if (k > result)
result = k;
return result;
cmov
指令的代码,这会对I-cache产生较小的负荷和分支预测器产生较小的压力,而不是条件分支。(此外,这段代码清晰易读。)如果你使用的是x86-64,编译器甚至会将所有内容保留在寄存器中。作为一种智力练习,我喜欢消除条件跳转。虽然我不知道这是否对性能有任何可衡量的影响 :)
#include <iostream>
#include <limits>
inline int max(int a, int b)
{
int difference = a - b;
int b_greater = difference >> std::numeric_limits<int>::digits;
return a - (difference & b_greater);
}
int max(int a, int b, int c)
{
return max(max(a, b), c);
}
int main()
{
std::cout << max(1, 2, 3) << std::endl;
std::cout << max(1, 3, 2) << std::endl;
std::cout << max(2, 1, 3) << std::endl;
std::cout << max(2, 3, 1) << std::endl;
std::cout << max(3, 1, 2) << std::endl;
std::cout << max(3, 2, 1) << std::endl;
}
cmov
解决方案可能更快。不确定这是否是最有效的方法,但可能是,并且肯定更短:
int maximum = max( max(i, j), k);
有一个提案将其纳入N2485下的C++库中。该提案很简单,因此我在下面包含了相关的代码。显然,这需要可变模板。
template < typename T >
const T & max ( const T & a )
{ return a ; }
template < typename T , typename ... Args >
const T & max( const T & a , const T & b , const Args &... args )
{ return max ( b > a ? b : a , args ...); }
在C++中找到2个或多个数字的最大值或最小值的最简单方法是:
int a = 3, b = 4, c = 5;
int maximum = max({a, b, c});
int a = 3, b = 4, c = 5;
int minimum = min({a, b, c});
mov eax, dword ptr [rsp + 8]
mov ecx, dword ptr [rsp + 4]
cmp eax, ecx
cmovl eax, ecx
mov ecx, dword ptr [rsp]
cmp eax, ecx
cmovl eax, ecx
与GCC类似,MSVC在循环中会出现混乱。
我认为你所说的“最高效”是指性能,尽量不浪费计算资源。但你可能也在谈论写更少的代码,或者关于源代码的可读性。我在下面提供了一个例子,你可以评估是否有用,或者你更喜欢从你收到的答案中选择另一个版本。
/* Java version, whose syntax is very similar to C++. Call this program "LargestOfThreeNumbers.java" */
class LargestOfThreeNumbers{
public static void main(String args[]){
int x, y, z, largest;
x = 1;
y = 2;
z = 3;
largest = x;
if(y > x){
largest = y;
if(z > y){
largest = z;
}
}else if(z > x){
largest = z;
}
System.out.println("The largest number is: " + largest);
}
}
/* 前提条件:i 是三个值中最大的。*/ int max(int i, int j, int k) { return i; }
或者可能只需返回42。 - Skurmedel