编译器能否省略已知条件的冗余if语句?传参方式有影响吗?
内联优化后条件判断次数与参数传递的影响
先看你给出的代码:
bool f(bool b) { if (b) return true; else return false; } std::unordered_map<int, int> my_map; bool find(int id) { auto it = my_map.find(id); if (it != my_map.end()) return true; else return false; } int main() { if (f(true)) std::cout << "It was true\n"; if (find(1)) std::cout << "Contains key\n"; }
内联优化后会不会只留一次判断?
分两种场景说:
针对
f(true):
编译器不仅会内联f函数,还因为传入的是常量true,直接在编译期把整个调用简化为true,连主函数里的if判断都会被彻底优化掉,直接执行输出语句——连一次判断都剩不下。如果是传变量,比如bool x = some_val(); if(f(x)),内联后会把函数逻辑直接合并成if(x),只保留一次判断,毕竟f的逻辑本质就是返回参数本身,多一层判断纯属鸡肋,编译器肯定会帮你合并。针对
find(1):
内联之后,主函数里的if(find(1))会直接替换成auto it = my_map.find(1); if(it != my_map.end()) { ... },原来函数内的判断(根据迭代器比较结果返回bool)和主函数的if会合并成一次——因为函数返回值就是it != my_map.end()的结果,内联后不需要多此一举再判断一次返回值,直接用这个比较结果作为if的条件,最终只会保留一次判断。
参数按值还是引用传递有影响吗?
基本没影响:
- 按值传递:像
f(bool b)这种,bool本身仅占1字节,拷贝成本可以忽略,内联时编译器直接把参数值代入逻辑,完全不影响判断合并。 - 按引用传递:哪怕改成
bool f(const bool& b),传常量true的话,编译器能直接把引用绑定的常量值代入,照样优化;传变量的话,内联后也会直接用原变量的判断逻辑,不会多出额外的判断。顶多是引用传递理论上涉及内存地址访问,但对于bool这种小类型,编译器基本会把引用优化成直接访问变量,不影响判断合并的逻辑。
说白了,只要编译器做内联优化,不管参数怎么传,最终都会把函数里的判断和主函数的判断合并,最多留一次判断(常量参数的情况直接消掉判断)。
内容的提问来源于stack exchange,提问作者Zebrafish
相关产品推荐
相关产品推荐

