【C++字符串】char*、const char*、char[]和std::string

专栏网址:https://blog.csdn.net/zhujushu/category_13112687.html

0.概述

在程序开发中,字符串操作是必不可少的功能之一。在众多编程语言中,C++对字符串有着底层、较良好的支持。

C++ 提供了以下两种字符串表示形式:

  • C语言风格 const char*、char[]、char* 等类型;
  • C++ std::string 类类型。

本文将介绍以上字符串类型使用的方式,并重点讲述std::string的功能。

1.const char*

const char* 是一个不可变的字符串常量类型,看以下代码:

const char* Str = "Hello World!";

里面 Str、"Hello World!" 都是const char*类型的,它可以是左值,也可以是右值。

注意区分const char* 和 char* const

char * const CConst;        //指向字符的静态指针
const char * ConstC;        //指向静态字符的指针

当const char*的值是一个右值时,C++编译器会在const char*的末尾添加'\0'。

2.char[]

char[]代表字符数组,可以对应一个字符串,如

char b[]="string2";
//b的长度是字符的数量+1
//因为C++编译器会在const char*的末尾添加'\0'

这里b是一个char数组(字符数组),每个元素对应一个字符,最后的元素为'\0'。

区别如下:

注意:char型数组的名字,也是该数组首元素的地址,是常量,不能改变。但char型数组的每个元素可以改变。

    char b[]="Hello World!";//定义
    printf("%s\n",b);//输出
    

    结果:
    Hello World!

    3.char*

    char* 是指向字符串的指针,与const char*不同的是,char*的值可以改变。

     看以下代码:

    char* Str = "Hello World!";//定义
    Str="Hi!";
    printf("%s\n",Str);

    输出:

    Hi!

    里面 Str是char*类型的。

    注意区分char[] 和 char* :

    char * C = "Hello!";
    C = "Hi!";//合法
    C[0] = 'A';//非法访问只读内存非法
    char CC[] = "Hello!";
    CC = "Hi!";//报错,首元素地址无法改变
    CC[0] = 'A';//合法

    在ISO C++中,char* 被指明是危险的,它可能导致内存泄漏、溢出等风险,在开发中要慎用。

    4.std::string

    std::string 是 C++ 标准库中提供的字符串类,用于处理动态大小的字符序列。它属于 std 命名空间,封装了字符串的存储和管理,提供了丰富的成员函数和操作符,简化了字符串操作。

    头文件

    使用std::string要引入<string.h>头文件,代码如下:

    #include <string.h>
    //using namespace std; //使用引入的标准库的全部内容,使用时无需std::前缀,但容易造成重声明和污染
    //using std::string; //同"using namespace std;",但只使用string类类型,推荐

    基本用法

    声明和初始化 std::string 可以通过多种方式完成:

    std::string str1;               // 默认初始化,空字符串
    std::string str2("Hello");      // 从 C 风格字符串初始化
    std::string str3(str2);         // 从另一个 std::string 初始化
    std::string str4(5, 'a');       // 重复字符初始化,结果为 "aaaaa"

    常用成员函数

    std::string 提供了大量成员函数,以下是一些常用功能:

    访问字符

    char c = str2[0]; // 通过下标访问,不检查边界 
    char c2 = str2.at(1); // 通过 at() 访问,会检查边界

    修改字符串

    str1.append(" World"); // 追加字符串 
    str1.push_back('!'); // 追加单个字符 
    str1.insert(5, " C++"); // 在指定位置插入 
    str1.erase(5, 4); // 删除子串

    容量操作

    size_t len = str1.size(); // 获取字符串长度 
    bool empty = str1.empty(); // 判断是否为空 
    str1.resize(10); // 调整字符串大小

    字符串操作

    查找和替换

    size_t pos = str1.find("World"); // 查找子串 
    if (pos != std::string::npos) { 
        str1.replace(pos, 5, "Universe"); // 替换子串 
    }

    子串提取

    std::string sub = str1.substr(6, 5);  // 提取从位置 6 开始的 5 个字符

    输入输出

    std::string 可以与标准输入输出流配合使用:

    std::string input;
    std::cin >> input;       // 读取一个单词
    std::getline(std::cin, input);  // 读取一行
    
    std::cout << input << std::endl;  // 输出字符串

    性能与注意事项

    • std::string 动态管理内存,自动处理存储空间的分配和释放。
    • 频繁的字符串拼接可能导致多次内存重新分配,影响性能。可以使用 reserve() 预分配空间优化。
    • 与 C 风格字符串交互时,可通过 c_str() 获取 const char* 指针:
    const char* cstr = str1.c_str();

    现代 C++ 扩展

    C++17 引入了 std::string_view,提供对字符串的非拥有视图,适合只读场景,避免不必要的拷贝:

    std::string_view view(str1.data(), 5);  // 创建前 5 个字符的视图

    5.总结

    C++提供了多种字符串处理方式,包括C风格字符串(const char*char[]char*)和更现代的std::string类。

    C风格字符串需要手动管理内存且易出错,而std::string通过自动内存管理简化了操作,并提供丰富的成员函数支持查找、替换、子串提取等常见需求。

    std::string与标准输入输出流无缝集成,同时支持通过c_str()与C风格字符串交互。

    C++17引入的std::string_view进一步优化了只读场景的性能。

    开发中应优先使用std::string以提升安全性和可维护性,仅在必要场景下谨慎使用C风格字符串。

    评论
    添加红包

    请填写红包祝福语或标题

    红包个数最小为10个

    红包金额最低5元

    当前余额3.43前往充值 >
    需支付:10.00
    成就一亿技术人!
    领取后你会自动成为博主和红包主的粉丝 规则
    hope_wisdom
    发出的红包
    实付
    使用余额支付
    点击重新获取
    扫码支付
    钱包余额 0

    抵扣说明:

    1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
    2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

    余额充值