C++字符串以及字符串的封装

这篇博客介绍了C++中如何对运算符进行重载以适应自定义类型,如自定义的MyString类。内容包括了C++标准库中的string类型的基本使用,如at()、size()等方法,并展示了自定义字符串类型MyString的构造、析构函数以及运算符重载(包括[]、=和+),强调了在自定义类型中进行边界检查的重要性。
摘要由CSDN通过智能技术生成

1.重载

        C++预定义中的运算符的操作对象只局限于基本的内置数据类型,但是对于我们自定义的类型

(类)是没有办法操作的

        但是大多时候我们需要对自定义的类型进行类似的运算,这个时候就需要我们对运算符进行

重新定义,赋予其新的功能,以满足自身的需求

2.string

        C语言之中是没有字符串类型的 只有字符串的表现形式 1.字符指针 2.字符数组

        在C使用字符串要注意:字符长度及尾\0的问题

        在C++的面向对象这个世界中,对于底层数据元素操作,我们把这个底层操作封装了起来,成

为了一个专属性字符串类型----string类型

       2.1 C++中string的API接口

#include <iostream>
using namespace std;
int main()
{
    string name1 = "gaowanxi";
    cout << name1 << endl;
    string name2 = "zhangsan";
    //at()接口
    cout << name2.at(2) << endl;
    //cout << name2.at(100) << endl;
    //size()接口
    cout << name2.size() << endl; //不包含尾部的'\0'
    //[]中括运算符函数的重载
    cout << name2[100] << endl;
    //在使用string定义的字符串,当访问指定的字符时,我们更推荐使用at,因为有边界检查
    //terminate called after throwing an instance of 'std::out_of_range'
    //what():  basic_string::at: __n (which is 6) >= this->size() (which is 5)

    operator+  +号运算符重载
    cout << name1 + name2 << endl;
    string str = name1 += name2;
    cout << str << "," << name1 <<endl;
    //append()接口
    string str2 = name2.append(",nihao");
    cout << str2 << "," <<  name2  << endl;
    return 0;
}

3.封装string类型

        3.1 构造函数

   //构造函数
    MyString(const char* c_str = nullptr){
        //1.获取外部字符串的长度
        int len = strlen(c_str);
        //2.开辟空间放置字符串
        this->my_data = new char[len+1];//+1 因为下标从0开始的
        //3.拷贝将字符串数据
        memmove(this->my_data,c_str,len);
        //4.结尾处加'\0'
        this->my_data[len]='\0';
    }
      //拷贝构造函数
    MyString(const MyString& other){
        int len = strlen(other.my_data);
        this->my_data = new char[len+1];
        memmove(this->my_data,other.my_data,len);
        this->my_data[len]='\0';
    }

        3.2 析构函数 

//析构函数
    ~MyString(){
        if(my_data != nullptr){
            delete []my_data;
            my_data = nullptr;
        }
    }

        3.3 运算符重载函数

    //获取字符串长度
    int size(){
        return strlen(this->my_data);
    }

    //括号运算符重载
    char operator[](int index){
        //1.判断index是否合法
        if(index < 0 || index  > this->size()){
            cout<<"越界"<<endl;
        }
        return this->my_data[index];
    }

    // = 号运算符重载
    MyString& operator=(const MyString& other){
        if(this == &other){
            //1.相等直接返回即可
            return *this;
        }
        //2.获取另一个字符串的长度
        int len = strlen(other.my_data);
        //3.如果本对象有指向空间 需要先释放 再开辟足够大的空间
        if(this->my_data != nullptr){
            delete []my_data;
            this->my_data = new char[len+1];
        }else{
            this->my_data = new char[len+1];
        }
        //4.拷贝数据
        memmove(this->my_data,other.my_data,len);
        this->my_data[len] = '\0';
        return *this;
    }

    //+号运算符重载
    MyString operator+(const MyString& other){
        //方法1. 使用系统函数
        //this->my_data = strncat(this->my_data,other.my_data,strlen(this->my_data) + strlen(other.my_data));

        //方法2. 使用自定义方法
        //1.重新定义长度
        int len = strlen(this->my_data) + strlen(other.my_data);
        //2. 开辟临时空间
        char *temp = new char[len+1];
        //3.分别将数据拷贝到临时空间中
        memmove(temp,this->my_data,strlen(this->my_data));
        memmove(temp + strlen(other.my_data),other.my_data,strlen(other.my_data));
        temp[len] = '\0';
        //4.清空this->my_data
        delete []this->my_data;
        //5.将临时空间赋值给this空间
        this->my_data = temp;

        return *this;
    }

    // 提供公有接口
    char* getMy_data(){
        return this->my_data;
    }

4.整体代码

#include <iostream>
#include <cstring>

using namespace std;
class MyString{
private:
    char* my_data;
public:
    //构造函数
    MyString(const char* c_str = nullptr){
        //1.获取外部字符串的长度
        int len = strlen(c_str);
        //2.开辟空间放置字符串
        this->my_data = new char[len+1];//+1 因为下标从0开始的
        //3.拷贝将字符串数据
        memmove(this->my_data,c_str,len);
        //4.结尾处加'\0'
        this->my_data[len]='\0';
    }
    //拷贝构造函数
    MyString(const MyString& other){
        int len = strlen(other.my_data);
        this->my_data = new char[len+1];
        memmove(this->my_data,other.my_data,len);
        this->my_data[len]='\0';
    }
    //析构函数
    ~MyString(){
        if(my_data != nullptr){
            delete []my_data;
            my_data = nullptr;
        }
    }
    //获取字符串长度
    int size(){
        return strlen(this->my_data);
    }
    //括号运算符重载
    char operator[](int index){
        //1.判断index是否合法
        if(index < 0 || index  > this->size()){
            cout<<"越界"<<endl;
        }
        return this->my_data[index];
    }
    // = 号运算符重载
    MyString& operator=(const MyString& other){
        if(this == &other){
            //1.相等直接返回即可
            return *this;
        }
        //2.获取另一个字符串的长度
        int len = strlen(other.my_data);
        //3.如果本对象有指向空间 需要先释放 再开辟足够大的空间
        if(this->my_data != nullptr){
            delete []my_data;
            this->my_data = new char[len+1];
        }else{
            this->my_data = new char[len+1];
        }
        //4.拷贝数据
        memmove(this->my_data,other.my_data,len);
        this->my_data[len] = '\0';
        return *this;
    }
    //+号运算符重载
    MyString operator+(const MyString& other){
        //方法1. 使用系统函数
        //this->my_data = strncat(this->my_data,other.my_data,strlen(this->my_data) + strlen(other.my_data));

        //方法2. 使用自定义方法
        //1.重新定义长度
        int len = strlen(this->my_data) + strlen(other.my_data);
        //2. 开辟临时空间
        char *temp = new char[len+1];
        //3.分别将数据拷贝到临时空间中
        memmove(temp,this->my_data,strlen(this->my_data));
        memmove(temp + strlen(other.my_data),other.my_data,strlen(other.my_data));
        temp[len] = '\0';
        //4.清空this->my_data
        delete []this->my_data;
        //5.将临时空间赋值给this空间
        this->my_data = temp;

        return *this;
    }
    // 提供公有接口
    char* getMy_data(){
        return this->my_data;
    }

};

  • 4
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值