用std::sort配合lambda比较器按长度排序字符串最直接:升序返回a.length()

用 std::sort 配合 lambda 比较器是最直接的方法
标准库的 std::sort 默认按字典序排 std::string,但你要的是按长度——必须显式提供比较逻辑。lambda 是最轻量、最安全的选择,不用写额外函数对象,作用域也干净。
升序(短→长):返回 a.length() ;降序(长→短):返回 <code>a.length() > b.length()。注意别写成 或 <code>>=,否则违反严格弱序,std::sort 行为未定义。
- 确保容器是可随机访问的,比如
std::vector<:string></:string>或原生数组(传首尾指针) - 如果用
std::array或 C 风格数组,记得用std::begin()/std::end()或计算指针边界 - 字符串含空格或 Unicode 不影响长度判断,
length()返回的是char数(不是字节数或码点数),这点要心里有数
原生 C 字符串数组(char*)要格外小心内存和空指针
如果你操作的是 char* strs[] = {"hello", "hi", "world!"} 这类指针数组,std::sort 依然能用,但比较器里必须先判空——strlen 遇到 nullptr 会崩溃,而 std::string 构造时遇到空指针也会抛异常。
推荐统一转成 std::string_view 做比较(C++17 起),避免拷贝又规避空指针风险:
std::sort(strs, strs + n, [](const char* a, const char* b) {
return std::string_view(a ? a : "").length()
- 不要直接对
char**排序后就认为字符串内容被移动了——你只是重排了指针,原始字符串字面量位置没变 - 如果数组里混着栈/堆分配的字符串,确保所有指针在整个排序过程中都有效
-
std::string_view的length()和std::string::length()行为一致,但不拥有数据,更轻量
稳定排序用 std::stable_sort,当长度相同时需保持原有相对顺序
比如你有一组字符串:{"a", "bb", "cc", "d"},按长度排完应该是 {"a", "d", "bb", "cc"};但如果原始中 "bb" 在 "cc" 前,而两者长度相同,你又希望它们在结果里仍保持这个顺序,就得用 std::stable_sort。
- 性能上,
std::stable_sort通常比std::sort略慢,空间开销略大,但多数场景差异可忽略 - 它对比较器的要求和
std::sort完全一样,lambda 写法不变 - 只有当你明确需要“同长度字符串不打乱原始次序”时才换,别默认用它
自定义结构体里存字符串?别忘重载 operator 或继续用 lambda
比如有个结构体 struct Item { std::string name; int id; };,你想按 name.length() 排。这时候有两种选择:要么给结构体加 operator,要么在 <code>sort 时用 lambda 访问成员。后者更灵活,尤其当你可能按不同字段多次排序时。
示例(按 name 长度升序):
std::sort(items.begin(), items.end(), [](const Item& x, const Item& y) {
return x.name.length()
- 如果结构体字段是
const或私有,lambda 里用const引用参数并确保访问函数是const成员函数 - 别在比较器里做耗时操作(如反复调用
name.substr(...)),提前算好长度缓存到变量里 - 如果这个排序逻辑在多处复用,可以封装成命名 lambda 或普通函数,但别为了“复用”强行加
operator——它语义应是自然序,不是临时业务规则
按长度排序本身不难,真正容易出问题的是边界:空字符串、空指针、混合内存模型、稳定性需求被忽略。把比较器写清楚,检查输入有效性,其余交给 std::sort 就行。
C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!











