如何简化从字符串首尾扫描子串的C++代码?
简化双向子串扫描的C++实现方案
针对重复循环代码的问题,可以通过参数化循环变量的方式,把正向、反向扫描的逻辑统一到一套循环中,彻底消除代码冗余。
核心思路
正向和反向扫描的差异仅集中在以下几点:
- 外层循环的起始值、终止条件、步长
- 内层循环的起始偏移、终止条件、步长
- 子串截取的起始索引和长度计算
我们可以把这些差异抽象为变量,根据reverse参数动态赋值,再复用同一套循环逻辑。
优化后的代码
#include <string> #include <unordered_set> std::string foo(const std::string& str, const std::unordered_set<std::string>& substrings, bool reverse = false) { // 初始化循环控制参数 const int i_start = reverse ? static_cast<int>(str.length()) : 0; const int i_end = reverse ? 0 : static_cast<int>(str.length()); const int i_step = reverse ? -1 : 1; std::string current_substr; for (int i = i_start; reverse ? (i > i_end) : (i < i_end); i += i_step) { // 内层循环的起始、终止、步长随reverse动态调整 for (int j = reverse ? i - 1 : i + 1; reverse ? (j > -1) : (j < static_cast<int>(str.length()) + 1); j += reverse ? -1 : 1) { // 统一子串截取逻辑 const size_t start_idx = reverse ? static_cast<size_t>(j) : static_cast<size_t>(i); const size_t len = reverse ? static_cast<size_t>(i - j) : static_cast<size_t>(j - i); current_substr = str.substr(start_idx, len); if (substrings.contains(current_substr)) { return current_substr; } } } return ""; // 补充未找到匹配时的返回值 }
关键优化点
- 参数化循环变量:通过
reverse参数动态设置循环的起始、结束值和步长,让同一套循环同时支持正向、反向扫描。 - 统一子串截取:根据
reverse判断子串的起始索引和长度,避免重复的substr调用逻辑。 - 性能优化:将函数参数改为
const引用,避免不必要的字符串和集合拷贝。
额外说明
当前写法兼顾了可读性和代码复用性,如果需要进一步精简,可以把循环的终止条件封装成辅助函数,但会增加额外的代码层级,按需选择即可。
内容的提问来源于stack exchange,提问作者commonelk
相关产品推荐
相关产品推荐

