0

哪个施工速度更快:

$a = $b * $c ? $b * $c : 0;  

或者

$i = $b * $c;  
$a = $i ? $i : 0;  

所有变量都是本地变量。

乘法,加法,减法和除法的速度是否不同?

更新:

这里有一些澄清:

  1. 这是一个关于从头开始编写速度优化代码的理论问题。不是关于“寻找瓶颈”。
  2. 我可以自己测量代码速度。但这不是关于使用 microtime() 的作业的问题。这是一个关于 PHP 解释器如何工作的问题(我试图通过自己挖掘谷歌来弄清楚但不安全)。
  3. 此外 - 我自己测量过,有点困惑。$a、$b 和 $c 的不同起始值(零、负、正、整数和浮点数的组合)在构造之间产生不同的结果。所以我很困惑。

BoltClock 为我提供了有用的信息,但 user576875 通过发布操作码解码器的链接让我很开心!他的回答也包含对我问题的直接回答。谢谢!

4

3 回答 3

10

如果你有 PHP 5.3,这会更快:

$a = $b * $c ?: 0; 

这与 相同$a = $b * $c ? $b * $c : 0;,但计算$a*$b只进行一次。此外,它不会像您的第二个解决方案那样执行额外的任务。

使用 Martin v. Löwis 的基准脚本,我得到以下时间:

$a = $b * $c ?: 0;               1.07s
$a = $b * $c ? $b * $c : 0;      1.16s
$i = $b * $c; $a = $i ? $i : 0;  1.39s

现在这些是微优化,因此在执行此操作之前可能有很多优化代码的方法:)

如果不是这样,您可能还想比较生成的 PHP OP 代码:

1 $a = $b * $c ? $b * $c : 0;

number of ops:  8
compiled vars:  !0 = $a, !1 = $b, !2 = $c
line     #  op                           fetch          ext  return  operands
-------------------------------------------------------------------------------
   1     0  MUL                                              ~0      !1($b), !2($c)
         1  JMPZ                                                     ~0, ->5
         2  MUL                                              ~1      !1($b), !2($c)
         3  QM_ASSIGN                                        ~2      ~1
         4  JMP                                                      ->6
         5  QM_ASSIGN                                        ~2      0
         6  ASSIGN                                                   !0($a), ~2
         7  RETURN                                                   null

2$i = $b * $c; $a = $i ? $i : 0;

number of ops:  8
compiled vars:  !0 = $i, !1 = $b, !2 = $c, !3 = $a
line     #  op                           fetch          ext  return  operands
-------------------------------------------------------------------------------
   1     0  MUL                                              ~0      !1($b), !2($c)
         1  ASSIGN                                                   !0($i), ~0
         2  JMPZ                                                     !0($i), ->5
         3  QM_ASSIGN                                        ~2      !0($i)
         4  JMP                                                      ->6
         5  QM_ASSIGN                                        ~2      0
         6  ASSIGN                                                   !3($a), ~2
         7  RETURN                                                   null

3 $a = $b * $c ?: 0;

number of ops:  5
compiled vars:  !0 = $a, !1 = $b, !2 = $c
line     #  op                           fetch          ext  return  operands
-------------------------------------------------------------------------------
   1     0  MUL                                              ~0      !1($b), !2($c)
         1  ZEND_JMP_SET                                     ~1      ~0
         2  QM_ASSIGN                                        ~1      0
         3  ASSIGN                                                   !0($a), ~1
         4  RETURN                                                   null

这些 OP 代码列表由VLD扩展生成。

于 2011-01-22T10:50:39.627 回答
1
<?php
function run(){
$b=10;
$c=10;
$start=gettimeofday(TRUE);
for($k=0;$k<10000000;$k++){
  $a = $b * $c ? $b * $c : 0;  
}
printf("%f\n", gettimeofday(TRUE)-$start);
$start=gettimeofday(TRUE);
for($k=0;$k<10000000;$k++){
  $i = $b * $c;  
  $a = $i ? $i : 0;  
}
printf("%f\n", gettimeofday(TRUE)-$start);
}
run();
?>

在我的系统(PHP 5.3.3,Linux,Core i7 2.8GHz)上,我得到

1.593521
1.512892

所以单独赋值会稍微快一些。另外,(+而不是*),我得到相反的结果:

1.386522
1.450358

所以你真的需要在你自己的系统上测量这些——使用不同的 PHP 版本,结果可能会再次改变。

于 2011-01-22T10:14:04.763 回答
0

您的两段代码各有一个缺点。一个人做额外的任务;另一个做额外的数学运算。最好两者都不做,使用 PHP 5.3 中的三元运算符,您可以:

$a = $b * $c ?: 0;

省略三元的第二部分会导致 PHP 将第一部分的结果放在那里。

使用 Martin v. Löwis 的基准测试代码,我认为这比任何一个都快 25%。

于 2011-01-22T10:47:33.713 回答