有效地找到最小值和最大值
Posted
技术标签:
【中文标题】有效地找到最小值和最大值【英文标题】:Finding minimum and maximum efficiently 【发布时间】:2014-01-09 09:56:14 【问题描述】:我有两个整数参数a
和b
。还有两个整数变量max
和min
。
我想将a
和b
的最大值分配给max
,并将两者中的最小值分配给min
。
我需要做这个操作数百万次,所以我想优化它。我目前正在做以下事情:
min = a < b ? a : b;
max = a > b ? a : b;
问题在于它需要两个 if 语句。我想知道是否有更好的方法来做到这一点。
【问题讨论】:
用什么语言?有些语言允许你做并行作业。 你可以使用 SSE 内在函数吗? 是的,我想,任何适用于 VS2012 的东西我都可以使用。 a 和 b 是从哪里来的? 它们是随机生成的。 【参考方案1】:std::tie(min, max) = std::minmax(a, b);
【讨论】:
【参考方案2】:if (a < b)
min = a; max = b;
else
min = b; max = a;
【讨论】:
是的,运行时间要少得多,谢谢! @BenjyKessler 你启用编译器优化了吗? 我使用的是 VS 2012,优化设置为最大化速度。【参考方案3】:您可能过早地进行了优化。看看编译器是怎么做的。
对于只有一个条件的版本,这很简单:-
if (a < b)
min = a;
max = b;
else
min = b;
max = a;
【讨论】:
【参考方案4】:或者你可能想使用一些数学:
int absdiff = abs (a-b);
int sum = a+b;
max = (sum+absdiff)/2;
min = (sum-absdiff)/2;
您可以相信编译器会根据基本类型优化所有内容,您可以摆脱分支并获得恒定的执行时间(不依赖于预测器)。
编辑:
英特尔处理器上的示例 abs 整数函数:
cdq
xor eax, edx
sub eax, edx
【讨论】:
abs()
通常是使用条件实现的,因此您仍然有一个分支。 int _RTLENTRYF _EXPFUNC abs(int i) return (i >= 0 ? i : -i);
有些输入不起作用,例如a = 1140851080; b = -158544698
当然。我们在这里谈论优化,否则您可以简单地采用a < b ? a : b
方式。最大值必须允许几个 MSB,但谁说这应该在完整的 32 位规模上工作?
好吧,只要我们都知道这些限制 :)
@harold 毕竟,单纯的整数减法已经是一个危险的陷阱;)【参考方案5】:
min=a;max=b;
if(a>b)
max=a;
min=b;
//Here you don't even need an else statement, i don't know how much time does else take but if it does then you have saved it.
【讨论】:
以上是关于有效地找到最小值和最大值的主要内容,如果未能解决你的问题,请参考以下文章