使用带lambda的std::max_element时,比较lambda的哪个参数为当前最大值?
关于std::max_element中lambda参数的明确说明
好问题!这确实是个容易搞混的细节,搞清楚之后能帮你简化代码逻辑。
直接给你结论:当你给std::max_element传入自定义比较lambda时,第一个参数是当前已经评估过的元素中的候选最大值,第二个参数是序列中正在被检查的新元素。
具体逻辑拆解
std::max_element的工作流程大概是这样的:
- 从序列的第一个元素开始,把它作为初始的候选最大值
- 然后依次遍历后续每个元素,每次调用你的lambda:把当前候选最大值传进第一个参数位置,把新遍历到的元素传进第二个参数位置
- 如果lambda返回
true,就意味着「第二个参数比第一个参数更大」,此时会把候选最大值更新为第二个元素;如果返回false,就保持当前候选最大值不变
举个和默认行为对齐的例子,默认的比较器是std::less<T>(),对应的lambda就是:
[](const auto& a, const auto& b) { return a < b; }
当b比a大时返回true,此时候选最大值就更新为b,完全符合我们找最大值的预期。
结合你的特殊值场景优化
现在你有一个始终视为最小的特殊值,比如叫SPECIAL_VAL,那你完全不用同时检查两个参数:
- 如果你想确保特殊值不会被选为最大值,那么当第二个参数是SPECIAL_VAL时,直接返回
false(因为新元素是最小的,不可能替换当前候选最大值);其他情况正常比较即可 - 反过来,如果当前候选最大值是SPECIAL_VAL(也就是遍历刚开始,或者之前的元素全是特殊值),那只要新元素不是SPECIAL_VAL,就返回
true,让新元素成为候选最大值
比如你的lambda可以写成这样(假设特殊值是-1,我们要找除了-1之外的最大值):
[](const auto& current_max, const auto& new_elem) { if (new_elem == -1) { return false; // 特殊值不可能比当前最大值大,不更新 } // 如果当前最大值是特殊值,那new_elem肯定更大,返回true;否则正常比较 return current_max == -1 || new_elem > current_max; }
这样就不用同时判断两个参数是不是特殊值,代码更简洁清晰~
内容的提问来源于stack exchange,提问作者Bonita Montero
相关产品推荐
相关产品推荐

