C++中的String的常用函数用法总结

在 C++ 中,std::string 是标准库提供的字符串类,功能强大且易用,定义在 <string> 头文件中。以下是对 std::string 常用函数的总结,包含用法、示例代码和注意事项,力求简洁全面,方便快速掌握。


1. 构造与初始化

  • 构造方式
  #include <string>
  #include <iostream>

  int main() {
      std::string s1;                    // 空字符串
      std::string s2("Hello");          // 从 C 风格字符串构造
      std::string s3(5, 'a');           // 5 个 'a',结果为 "aaaaa"
      std::string s4(s2);               // 拷贝构造
      std::string s5(s2, 1, 3);         // 从 s2 的索引 1 开始,取 3 个字符,结果为 "ell"
      std::string s6 = "World";         // 赋值初始化

      std::cout << s2 << std::endl;     // 输出: Hello
      return 0;
  }
  • 注意
  • std::string 自动管理内存,无需手动分配或释放。
  • 支持 C 风格字符串(如 const char*)和 std::string 之间的转换。

2. 基本操作

  • 访问字符
  • s[i]:通过索引访问字符(可能抛出越界异常)。
  • s.at(i):通过索引访问字符,带边界检查,抛出 std::out_of_range
  std::string s = "Hello";
  char c1 = s[1];      // 'e'
  char c2 = s.at(1);   // 'e'
  • 长度与容量
  • s.length()s.size():返回字符串长度(字符数)。
  • s.empty():检查是否为空。
  • s.capacity():返回当前分配的存储空间大小。
  • s.reserve(n):预分配存储空间,避免频繁重新分配。
  • s.shrink_to_fit():释放多余容量(C++11 起,非强制)。
  std::string s = "Hello";
  std::cout << s.size() << std::endl;    // 5
  std::cout << s.empty() << std::endl;   // 0 (false)
  s.reserve(100);                        // 预分配空间
  • 清空与调整
  • s.clear():清空字符串。
  • s.resize(n):调整字符串长度为 n,填充默认字符(通常为 \0)。
  • s.resize(n, c):调整长度为 n,填充字符 c。
  std::string s = "Hello";
  s.clear();               // s 变为空
  s.resize(3, 'x');        // s 变为 "xxx"

3. 字符串修改

  • 拼接
  • s += str:追加字符串或字符。
  • s.append(str):追加字符串。
  • s.append(n, c):追加 n 个字符 c。
  • s.push_back(c):追加单个字符。
  std::string s = "Hello";
  s += " World";           // "Hello World"
  s.append(3, '!');        // "Hello World!!!"
  s.push_back('?');        // "Hello World!!!?"
  • 插入
  • s.insert(pos, str):在位置 pos 插入字符串 str。
  • s.insert(pos, n, c):在位置 pos 插入 n 个字符 c。
  std::string s = "Hello";
  s.insert(1, "XX");       // "HXXello"
  s.insert(2, 2, 'Y');     // "HXYYello"
  • 删除
  • s.erase(pos, n):从位置 pos 开始删除 n 个字符。
  • s.pop_back():删除最后一个字符(C++11 起)。
  std::string s = "Hello";
  s.erase(1, 2);           // "Hlo"
  s.pop_back();            // "Hl"
  • 替换
  • s.replace(pos, n, str):从位置 pos 开始,替换 n 个字符为 str。
  std::string s = "Hello";
  s.replace(1, 3, "XXX");  // "HXXXo"

4. 字符串查找

  • 查找子串
  • s.find(str, pos):从 pos 开始查找子串 str,返回首次出现位置,未找到返回 std::string::npos
  • s.rfind(str, pos):从 pos 开始反向查找。
  std::string s = "Hello World";
  size_t pos = s.find("World");    // 6
  size_t rpos = s.rfind("l");      // 9
  • 查找字符
  • s.find_first_of(str, pos):查找 str 中任意字符首次出现的位置。
  • s.find_last_of(str, pos):查找 str 中任意字符最后出现的位置。
  std::string s = "Hello";
  size_t pos = s.find_first_of("lo");  // 2 ('l')
  size_t last = s.find_last_of("lo");  // 4 ('o')
  • 查找不匹配
  • s.find_first_not_of(str, pos):查找第一个不属于 str 的字符。
  std::string s = "Hello";
  size_t pos = s.find_first_not_of("Hel");  // 3 ('o')

5. 子串与比较

  • 获取子串
  • s.substr(pos, n):从 pos 开始取 n 个字符。
  std::string s = "Hello World";
  std::string sub = s.substr(6, 5);  // "World"
  • 比较
  • s.compare(str):比较字符串,等于 0,小于返回负值,大于返回正值。
  • 直接使用 ==, <, > 等操作符。
  std::string s1 = "apple";
  std::string s2 = "banana";
  if (s1 < s2) std::cout << "s1 < s2" << std::endl;  // 输出

6. 转换与输入输出

  • 与 C 风格字符串转换
  • s.c_str():返回 const char*,以空字符结尾。
  • s.data():返回字符数组指针(C++11 起,可修改)。
  std::string s = "Hello";
  const char* cstr = s.c_str();  // "Hello"
  • 数字与字符串转换(C++11 起):
  • std::to_string(val):将数字转换为字符串。
  • std::stoi(s), std::stol, std::stod:字符串转数字。
  std::string s = std::to_string(123);  // "123"
  int n = std::stoi("456");            // 456
  • 输入输出
  • 使用 std::cinstd::cout
  std::string s;
  std::getline(std::cin, s);  // 读取整行
  std::cout << s << std::endl;

7. 迭代与遍历

  • 迭代器
  • s.begin(), s.end():返回字符串的起始和结束迭代器。
  • s.rbegin(), s.rend():反向迭代器。
  std::string s = "Hello";
  for (auto it = s.begin(); it != s.end(); ++it) {
      std::cout << *it;  // H e l l o
  }
  • 范围 for 循环(C++11 起):
  for (char c : s) {
      std::cout << c;  // H e l l o
  }

8. 注意事项与最佳实践

  • 越界检查
  • 使用 at() 而非 [] 以确保边界安全,捕获 std::out_of_range 异常。
  • 性能优化
  • 使用 reserve() 预分配空间,减少动态分配。
  • 避免频繁拼接小字符串,考虑使用 std::stringstream 或预分配。
  • 异常处理
  • stoi, at 等可能抛出异常,需用 try-catch 处理:
  try {
      int n = std::stoi("abc");  // 抛出 std::invalid_argument
  } catch (const std::exception& e) {
      std::cerr << "Error: " << e.what() << std::endl;
  }
  • 编码问题
  • std::string 处理的是字节序列,处理 Unicode 时需使用 std::wstring 或第三方库(如 ICU)。
  • C++17/20 新特性
  • C++17 引入 std::string_view,用于只读字符串视图,避免拷贝。
  std::string_view sv = "Hello";
  std::cout << sv << std::endl;  // Hello

9. 示例综合应用

以下是一个综合示例,展示字符串操作的常见场景:

#include <iostream>
#include <string>

int main() {
    std::string s = "Hello, World!";

    // 基本信息
    std::cout << "Length: " << s.size() << std::endl;  // 13

    // 查找与替换
    size_t pos = s.find("World");
    if (pos != std::string::npos) {
        s.replace(pos, 5, "C++");
    }
    std::cout << "After replace: " << s << std::endl;  // Hello, C++!

    // 拼接与插入
    s += " Welcome";
    s.insert(7, "Great ");  // Hello, Great C++! Welcome
    std::cout << s << std::endl;

    // 子串
    std::string sub = s.substr(7, 5);  // Great
    std::cout << "Substring: " << sub << std::endl;

    // 遍历
    for (char& c : s) {
        c = std::toupper(c);  // 转换为大写
    }
    std::cout << "Uppercase: " << s << std::endl;  // HELLO, GREAT C++! WELCOME

    return 0;
}

10. 总结

std::string 提供了丰富的接口,涵盖字符串的构造、修改、查找、比较和转换等功能。通过熟练使用上述函数,并结合迭代器、异常处理和性能优化技巧,可以高效处理字符串相关任务。建议通过编写小项目(如文本解析器或字符串处理工具)巩固掌握。

如果需要针对特定场景的深入讲解或更多示例,请告诉我!

类似文章

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注