最推荐用 reserve + append 循环实现字符串重复:先调用 result.reserve(s.size() * n) 预分配内存,再循环调用 result.append(s),避免多次内存重分配,兼顾效率与可读性。

用 std::string 构造函数最直接
如果只是重复一个固定字符串(比如 "abc")N 次,std::string 自带的构造函数就能搞定:std::string(size_t n, char c) 适用于单字符,但对多字符要用 std::string 的重复拼接方式——更推荐用 std::string 的构造 + operator+ 或 append。
实际最常用、最高效的是:先构造一个空串,再用 append 循环 N 次。比反复 += 少内存重分配:
std::string repeat(const std::string& s, size_t n) {
std::string result;
result.reserve(s.size() * n); // 预分配避免多次 realloc
for (size_t i = 0; i
-
reserve()很关键——不加的话,N 较大时可能触发多次内存拷贝 - 传入
n == 0或s.empty()都能安全处理,不用额外判断 - 不要用
result += s在循环里,尤其 N > 1000 时性能明显下降
用 std::string 的 assign 方法一行解决
如果你重复的是单个字符(如 'x'),直接用构造函数:std::string(n, 'x') 最简洁。
但如果是字符串字面量或变量,C++20 之前没有内置“repeat string”函数,不过可以用 assign 搭配迭代器技巧(稍绕但无循环):
std::string s = "ab"; size_t n = 3; std::string result; result.assign(n, '\0'); // 先占位 for (size_t i = 0; i <p>这写法易出错且不直观,不推荐。老老实实用 <code>append</code> 循环更清晰可靠。</p><div class="aritcle_card flexRow artxards"> <div class="artcardd flexRow"> <a class="aritcle_card_img" rel="nofollow" href="/xiazai/skill2659" title="C++"><img src="https://img.php.cn/upload/skill/000/000/081/178927213426672.jpg" alt="C++" onerror="this.onerror='';this.src='/static/lhimages/moren/morentu.png'" ></a> <div class="aritcle_card_info flexColumn"> <a rel="nofollow" href="/xiazai/skill2659" title="C++" class="overflowclass">C++</a> <p class="overflowclass">"空空如也"</p> </div> <a rel="nofollow" href="/xiazai/skill2659" title="C++" class="aritcle_card_btn flexRow flexcenter"><b></b><span>下载</span> </a> </div> </div>
-
assign本身是覆盖语义,不是追加,容易误清空已有内容 - 手动计算偏移 +
std::copy容易越界,尤其s含 null 字符时 - 除非在极度受限环境(禁用循环),否则没必要这么写
用 C++20 的 <ranges></ranges> 和 views::repeat?别踩坑
std::views::repeat 是重复一个值(如 char 或 int),不是重复整个 std::string。它返回的是 view,不能直接转成 std::string,而且对字符串片段做 repeat 后再 join 没有标准库支持。
下面这段代码看似可行,实际编译失败或行为未定义:
// ❌ 错误示例
auto r = std::views::repeat("ab", 3); // 类型是 repeat_view<const char>,不是 string_view
std::string result(r.begin(), r.end()); // error: no matching constructor</const>
-
std::views::repeat不接受std::string作为被重复对象(只接受可复制的T,但 string 的 view 语义复杂) - 即使你用
std::views::repeat(s),得到的是repeat_view<:string></:string>,它的迭代器解引用返回的是std::string&,不能直接用于构造新 string - 想用 ranges 做这事,得组合
views::join+views::transform,代码冗长且效率不如手写 loop
第三方库或宏?谨慎引入
Boost 有 boost::algorithm::join,但没直接的 repeat;fmt、abseil 等也未提供字符串重复工具。自己写个 inline 函数比拉依赖更轻量。
- 宏(如
#define REPEAT(s, n) ...)无法处理运行时n,且类型不安全 - 某些头文件里封装的
str_repeat可能内部没reserve,大数据量下慢一倍以上 - 如果项目已用
string_view,注意传入的s生命周期必须长于函数调用——别传临时std::string("abc").c_str()
真正要注意的只有两点:预分配内存、别迷信“一行流式写法”。其它都是干扰项。
C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!










