c – 处理器实际上是否计算乘以零或一?为什么?
发布时间:2020-12-16 04:51:16 所属栏目:百科 来源:网络整理
导读:简短版 在以下行中: aData[i] = aData[i] + ( aOn * sin( i ) ); 如果aOn为0或1,处理器是否实际执行乘法,还是有条件地计算结果(0表示0,其他值表示1)? 长版 我正在研究算法性能的一致性,其中部分涉及到Branch Prediction的效果. 假设是这段代码: for ( i =
简短版
在以下行中: aData[i] = aData[i] + ( aOn * sin( i ) ); 如果aOn为0或1,处理器是否实际执行乘法,还是有条件地计算结果(0表示0,其他值表示1)? 长版 我正在研究算法性能的一致性,其中部分涉及到Branch Prediction的效果. 假设是这段代码: for ( i = 0; i < iNumSamples; i++ ) aData[i] = aData[i] + ( aOn * sin( i ) ); 将提供比此代码更稳定的性能(分支预测可能会破坏性能): for ( i = 0; i < iNumSamples; i++ ) { if ( aOn ) aData[i] = aData[i] + sin( i ); } aOn为0或1,它可以在循环执行期间由另一个线程切换. 实际的条件计算(上例中的sin(i))涉及更多的处理,if条件必须在循环内(有很多条件,不仅仅是上面例子中的一个;同样,aOn的变化应该有效立即而不是每个循环). 忽略性能一致性,两个选项之间的性能权衡是执行if语句和乘法的时间. 无论如何,很容易发现如果处理器不能对1和0之类的值执行实际乘法,则第一个选项可能是双赢解决方案(没有分支预测,性能更好). 解决方法
处理器使用0和1执行常规乘法.
原因是,如果处理器在每次计算之前检查0和1,则引入条件将需要更多周期.虽然您将获得0和1乘数的性能,但您将失去任何其他值的性能(更有可能). 一个简单的程序可以证明: #include <iostream> #include "cycle.h" #include "time.h" void Loop( float aCoefficient ) { float iSum = 0.0f; clock_t iStart,iEnd; iStart = clock(); for ( int i = 0; i < 100000000; i++ ) { iSum += aCoefficient * rand(); } iEnd = clock(); printf("Coefficient: %f: %li clock ticksn",aCoefficient,iEnd - iStart ); } int main(int argc,const char * argv[]) { Loop( 0.0f ); Loop( 1.0f ); Loop( 0.25f ); return 0; } 输出为: Coefficient: 0.000000: 1380620 clock ticks Coefficient: 1.000000: 1375345 clock ticks Coefficient: 0.250000: 1374483 clock ticks (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |