热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

c++如何处理0*(大表达式)-Howdoesc++handle0*(largeexpression)

Concerningspeed,ifIneedtocalculatealargeexpression,say:关于速度,如果我需要计算一个大表达式,请说:switch1*(l

Concerning speed, if I need to calculate a large expression, say:

关于速度,如果我需要计算一个大表达式,请说:

switch1*(large expression 1)+switch2*(large expression 2)

Depending on my input, switch1 can be 0 or 1, as can switch2 be. What would be the quickest for c++ to do, making an if statement or write it down as above?

根据我的输入,switch1可以是0或1,switch2也可以。什么是c ++最快的做法,如上所述制作if语句或将其写下来?

5 个解决方案

#1


0  

So, essentially you are asking about Short-Circuit Evaluation, and you are asking whether C++ does it for arithmetic expressions besides boolean expressions.

所以,基本上你要问的是短路评估,你问的是C ++是否为除了布尔表达式之外的算术表达式做了。

It is kind of hard to prove a negative, but as far as I know, C++ only does short-circuit evaluation for logical expressions, so there is no equivalent for arithmetic expressions. Also, I can think of plenty of code that would horribly break if arithmetic expressions were being evaluated in a short-circuit fashion, so I don't think that could ever be so.

很难证明是消极的,但据我所知,C ++只对逻辑表达式进行短路评估,因此算术表达式没有等价物。此外,如果算术表达式以短路方式进行评估,我可以想到大量代码会严重破坏,所以我认为不会如此。

#2


0  

Theoretically, the compiler could generate code to avoid computing the expression if it could show that it had no side-effects. But in practice, it's unlikely to add code to check if the value is zero because it has no reason to think that it will be.

从理论上讲,编译器可以生成代码,以避免计算表达式,如果它可以显示它没有副作用。但实际上,它不太可能添加代码来检查值是否为零,因为它没有理由认为它会是。

On the other hand, logical operations (|| and &&) are guaranteed to short-circuit in C++. So you should use them.

另一方面,逻辑运算(||和&&)保证在C ++中短路。所以你应该使用它们。

#3


0  

result = 0;
if(switch1) {
    result += large_expresion_1();
}
if(switch2)
    result += large_expression2();
}

But if you are optimising "large expressions" be sure to check whether it's actually quicker to calculate them both then add them in a branchless manner. eg something like

但是如果你正在优化“大表达式”,一定要检查它们是否实际上更快计算它们然后以无分支方式添加它们。比如像

result = ((-(uint64_t)(switch1)) & large_expression_1) + ((-(uint64_t)(switch2)) & large_expression_2);

A bunch of such bithacks are documented here: https://graphics.stanford.edu/~seander/bithacks.html

这里记录了一堆这样的比特:https://graphics.stanford.edu/~seander/bithacks.html

Benchmark and separate to that, read the generated assembly language to find out what the compiler is actually doing for (or to) you.

基准测试并与之分离,读取生成的汇编语言,以找出编译器实际为您(或)做的事情。

#4


0  

switch1 can be 0 or 1, as can switch2 be

switch1可以是0或1,switch2也可以

If switch1 and switch2 can really only have values of 0 or 1 then it would be better for them to be booleans rather than integers.

如果switch1和switch2实际上只能有0或1的值,那么它们更好的是布尔值而不是整数。

With boolean switches, your statement becomes:

使用布尔开关,您的语句变为:

result = (switch1 ? (large expression 1) : 0)
       + (switch2 ? (large expression 2) : 0)

It is the case that in this form, the expressions will be computed even if their result won't be used. A simple and clear way to avoid wasted computation is the obvious one:

在这种形式下,表达式将被计算,即使它们的结果不会被使用。避免浪费计算的一种简单明了的方法是显而易见的:

result = 0;
if(switch1) {
    result += large expression 1;
}
if(switch2) {
    result += large expression 2;
}

You could tidy this up by extracting methods, into which you pass the switches:

你可以通过提取传递开关的方法来整理它:

result = guardedLargeExpression1(switch1, otherparams1) 
       + guardedLargeExpression2(switch2, otherparams2);

... with ...

...... ......

int guardedLargeExpression1(bool switch, foo params) {
    if(switch) {
        return 0;
    }
    return large expression(...);
}

You could also do clever stuff with pointers to functions:

您还可以使用指向函数的指针做一些聪明的事情:

int guardedFunctionCall(bool switch, int *functionptr(foo), foo arg) {
    if(switch) {
        return 0;
    }
    return (*functionptr)(arg);
}

... which is approaching the kind of thing you'd do in Java when you lazily evaluate code using a Supplier.

...当您懒惰地使用供应商评估代码时,这正在接近您在Java中所做的事情。

Or, since you're in C++ not C, you can do something more OO and actually use the C++ equivalent of Supplier: What is the C++ equivalent of a java.util.function.Supplier?

或者,既然您使用的是C ++而不是C,那么您可以执行更多OO并实际使用C ++等效的Supplier:什么是java.util.function.Supplier的C ++等价物?

#5


0  

If depends on the exact conditions. CPU, compiler, the exact expressions.

如果取决于具体条件。 CPU,编译器,确切的表达式。

An if can slow down a program, if if becomes a conditional jump in the assembly code, and the condition cannot be predicted.

如果if成为汇编代码中的条件跳转,并且无法预测条件,则if可以减慢程序的速度。

If the conditional cannot be predicted, and the "large expressions" are actually simple, it may be faster to do the "multiply-way".

如果无法预测条件,并且“大表达式”实际上很简单,那么执行“乘法”可能会更快。

However, if the expressions are slow to calculate, or the if can be branch predicted perfectly (or it doesn't compile to a conditional jump), then I think the if way will be faster.

但是,如果表达式的计算速度很慢,或者if可以完美地分支预测(或者它没有编译成条件跳转),那么我认为if方式会更快。

All in all, you should try both solutions, and check which is faster.

总而言之,您应该尝试两种解决方案,并检查哪种解决方案更快。


推荐阅读
author-avatar
阿离说你是宝贝
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有