C++20起可用std::erase(s, '>')一行安全移除所有'>'字符;旧标准需用s.erase(remove(s.begin(), s.end(), '>'), s.end()),二者均等价于erase-remove惯用法且避免迭代器失效。

用 std::erase 直接移除所有 '>'
C++20 起,std::string 支持 std::erase(非成员函数),一行就能删掉所有指定字符,无需手写循环或 remove_if。它内部调用 erase-remove 惯用法,但封装得干净,语义明确。
常见错误是误用 std::remove 后忘记调用 erase,导致“逻辑删除”却没真正缩短字符串——std::erase 一步到位,避免这个坑。
- 只适用于 C++20 及以上;若项目是 C++17 或更早,跳到下一节
- 对空字符串、无
'>'的字符串安全,返回值是被删字符个数,可忽略 - 性能上等价于手动
erase(remove(...)),但更不易出错
std::string s = "a>b<c>d"; std::erase(s, '>'); // s 变成 "ab<cd"
兼容 C++11/14/17:用 erase + remove 组合
老标准下必须显式组合 std::remove 和 std::string::erase。注意:不能只调 std::remove,它只是把目标字符“挪到末尾”,不改变 size()。
容易漏掉的是迭代器类型匹配——std::remove 返回的是 std::string::iterator,必须传给 erase 的迭代器重载,而非索引重载。
立即学习“C++免费学习笔记(深入)”;
-
std::remove(s.begin(), s.end(), '>')返回新逻辑结尾位置 -
s.erase(...)必须用该迭代器作为起点,第二个参数用s.end() - 别写成
s.erase(std::remove(...), s.length())—— 编译不过
std::string s = "x>y>z"; s.erase(std::remove(s.begin(), s.end(), '>'), s.end()); // s 变成 "xyz"
如果字符串里有 HTML 实体 > 怎么办?
题目说“去掉所有大于号”,但实际场景中,字符串可能来自 HTML 或 XML 解析结果,里面混着 > 这种转义序列。直接删 '>' 会破坏语义——你可能想还原后再删,或只删原生 > 而保留转义。
没有银弹,得先明确需求:
- 只要删字面量
>(即 ASCII 62),不管上下文 → 前两节方法完全适用 - 想先解码 HTML 实体再删所有
>→ 需引入轻量 HTML 解码逻辑(如简单替换">"→">"),再走std::erase - 要保留
>不动,只删裸>→ 前两节方法也适用,因为>是四个字符,不会被当成单个>
多数情况属于第一种;若涉及 HTML,务必确认输入来源和业务含义,别默认“所有 > 都该删”。
性能与边界注意点
对短字符串(
-
std::erase和erase+remove都是 O(n),仅遍历一次,内存连续,CPU 缓存友好 - 别用
find+erase(pos, 1)循环——每次erase都触发内存搬移,最坏 O(n²) - 如果字符串是 const 或不可修改(比如
const std::string&),得先拷贝再处理 - 宽字符(
std::wstring)同理,但需确保用L'>',且编译器支持宽字符版本的std::erase(C++20 起支持)
真正容易被忽略的是:是否要保留原始字符串不变?是否在多线程里共享该字符串?这些决定了你该用原地修改还是构造新字符串——而上面所有示例都是就地修改。


















