std::min和三元运算符在性能方面的差异?

8

在使用 <script> 标签时,是否存在性能差异?

a = a <= b ? a : b;

对比

a = std::min(a, b);

我正在处理的代码中使用了第一种形式,但变量名很长,这使得代码难以阅读。我更喜欢使用第二种形式,但不确定是否会有性能差异。

5个回答

13

我使用gcc -O2对其进行了测试,两者生成的汇编代码完全相同,没有任何区别。


7

优先关注代码的清晰度而非过早的优化。

即使两个版本之间存在性能差异[*],只有当这行代码是整个性能瓶颈的一部分时才会有影响: 请阅读 阿姆达尔定律

[*] 实际上,这种性能差异可能并不会对性能造成明显的影响。如果你真的非常想知道,唯一找出确切答案的方法是构建一些代表性的基准测试,并使用您的工具链构建它们,在目标架构上运行。


3
这是我的标准库实现(gcc5)的样子:
template<typename _Tp>
    _GLIBCXX14_CONSTEXPR
    inline const _Tp&
    min(const _Tp& __a, const _Tp& __b)
    {
      // concept requirements
      __glibcxx_function_requires(_LessThanComparableConcept<_Tp>)
      //return __b < __a ? __b : __a;
      if (__b < __a)
    return __b;
      return __a;
    }

因此,当内联此函数并开启所有优化时,std::min的代码速度将达到最快。微观优化通常不是程序的瓶颈。

手写版本可能会通过值返回,这样更容易进行优化。 - Alan Stokes
@AlanStokes 而且这样也会稍微更安全,因为如果你执行 const int& x = min(n+1, n-1);,你最终会得到一个悬空引用。 - vsoftco
@vsoftco 在这种情况下,临时变量的生命周期不会被延长到 x 的生命周期吗? - Tristan Brindle
1
Not via return of a function - vsoftco

1
这是您需要进行一些性能分析的地方。但是,您可能会发现没有区别,因为两个语句可能会生成完全相同的代码(查看生成的汇编代码可以帮助您--使用g++,请使用-S进行编译)。

1
在clang和启用优化的gcc中,它们都会生成相同的汇编代码:
    cmp     esi, edi
    cmovle  edi, esi
    mov     eax, edi

请查看此链接:https://godbolt.org/g/eWsJl9

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接