当前位置: 首页 > news >正文

C++类的模拟实现

📟作者主页:慢热的陕西人

🌴专栏链接:C++

📣欢迎各位大佬👍点赞🔥关注🚓收藏,🍉留言

本博客主要内容讲解了简单模拟实现string类

C++类的模拟实现

文章目录

  • C++类的模拟实现
    • @[toc]
    • Ⅰ.默认成员函数部分
    • Ⅱ. 常用成员函数的实现
    • Ⅲ. 运算符以及输入输出流的重载
    • Ⅳ. 迭代器实现

Ⅰ.默认成员函数部分

①构造函数

选择使用了带有缺省参数的构造函数写法:当没有传入字符串的时候,选择将string中的字符串初始化为空串。

初始化列表部分只对_size进行了初始化。

string(const char* str = "")
:_size(strlen(str))
{_capacity = _size == 0 ? 3 : _size;_str = new char[_capacity + 1];//+1因为要多以\0strcpy(_str, str);
}

②拷贝构造函数

拷贝构造函数是相当重要的,因为默认生成的拷贝构造函数只能实现浅拷贝,所以我们要自己来实现。

因为string类中涉及到了指针指向空间的问题所以在拷贝的时候也是需要新new一个空间出来的,这样就不会造成一份空间被析构两次的情况了

string(const string& s)
:_size(s._size)
,_capacity(s._capacity)
{_str = new char[_capacity + 1];strcpy(_str, s._str);
}

③析构函数

析构函数用于释放和清理string类实例化产生的空间。

~string()
{delete[] _str;_str = nullptr;_capacity = 0;_size = 0;
}

Ⅱ. 常用成员函数的实现

  • c_str()

    用于返回string的字符串内容的函数。

    char* c_str()
    {return _str;
    }
    
  • swap()

    用于交换两个string类的函数

    void swap(string& s)
    {std::swap(_str, s._str);std::swap(_size, s._size);std::swap(_capacity, s._capacity);
    }
    
  • find()

    ①从pos位置开始在字符串寻找和ch相同的字符,并返回它第一次出现的位置

    ② 从pos位置开始在字符串寻找和str相同的字符串,并返回它第一次出现的位置

    size_t find(char ch, size_t pos = 0)
    {assert(pos <= _size);for (int i = pos; i < _size; i++){if (_str[i] == ch){return i;}}return npos;
    }
    size_t find(const char* str, size_t pos = 0)
    {assert(pos <= _size);char* p = strstr(_str + pos, str);if (p == nullptr){return npos;}else{return p - _str;}
    }
    
  • clear()

    用于将string中的字符串清空的函数

    void clear()
    {_str[0] = '\0';_size = 0;
    }
    
  • reserve()

    用于改变string容量的函数,一般用于扩容。

    void reserve(size_t n)
    {char* temp = new char[n + 1];strcpy(temp, _str);delete[] _str;_str = temp; _capacity = n;
    }
    
  • insert()

    向字符串的pos位置插入字符或者字符串。

    string& insert(size_t pos, char ch)
    {assert(pos <= _size);if (_size + 1 > _capacity){reserve(2 * _capacity);}错误问题会导致死循环//size_t end = _size;//while (end > pos)//{//	_str[end + 1] = _str[end];//	--end;//}size_t end = _size + 1;while (end > pos){_str[end] = _str[end - 1];--end;}_str[pos] = ch;++_size;return *this;}string& insert(size_t pos, const char* str){assert(pos <= _size);size_t len = strlen(str);//挪动数据size_t end = _size + len;if (_size + len > _capacity){reserve(_size + len);}while (end - len  + 1 > pos){_str[end] = _str[end - len];--end;}_size += len;//拷贝数据strncpy(_str + pos, str, len);return *this;}
    
  • erase()

    将字符串pos位置以及其之后的len长度的字符串都都删掉

    string& erase(size_t pos, size_t len = npos)
    {if (len == npos || pos + len >= _size){_str[pos] = '\0';_size = pos;}else{strcpy(_str + pos, _str + pos + len);_size -= len;}return *this;
    }
    
  • resize()

    改变字符串的大小,这里给了一个缺省参数,也就是当我们是要增大字符串的大小的时候可以给这个缺省值也可以不给。

    void resize(size_t n, char ch = '\0')
    {if (n < _size){	_size = n;_str[n] = '\0';}else if(n > _size){if (n > _capacity){reserve(n);}int i = _size;while (i < n){_str[i] = ch;++i;}_size = n;_str[n] = '\0';}
    }
    
  • pushback()

    向字符出串尾部插入字符

    void push_back(char ch)
    {//if (_size + 1 > _capacity)//{//	reserve(2 * _capacity);//}//_str[_size] = ch;//++_size;//_str[_size] = '\0';apend(&ch);//insert函数的复用insert(_size, ch);
    }
    
  • apend()

    向字符串尾部追加字符串

    void apend(const char* str)
    {//int len = strlen(str);//if (_size + len > _capacity)//{//	reserve(_size + len);//}//strcpy(_str + _size, str);//_size += len;//insert函数的复用insert(_size, str);
    }
    

Ⅲ. 运算符以及输入输出流的重载

①运算符重载

bool operator<(const string& s) const
{return strcmp(_str, s._str) < 0;
}
bool operator==(const string& s) const
{return strcmp(_str, s._str) == 0;
}
bool operator>(const string& s) const
{return !(*this < s  && *this == s);
}
bool operator>=(const string& s) const
{return *this > s || *this == s;
}
bool operator<=(const string& s) const
{//这里给函数加上const才可以交换s和*this的值//因为不加const的话相当于是用s去调==的函数//但是因为s是一个const类型的,所以是权限的放大//所以结论就是对于不修改成员变量的函数最好加上constreturn *this < s || s == *this;
}
bool operator!=(const string& s) const
{return !(*this == s);
}
string& operator=(const string& s)
{if (this != &s){//delete[] _str;//_str = new char[_capacity + 1];//strcpy(_str, s._str);//_capacity = s._capacity;//_size = s._size;char* temp = new char[_capacity + 1];strcpy(temp, s._str);delete[] _str;_str = temp;_capacity = s._capacity;_size = s._size;}return *this;
}

②流插入和流输出重载

	ostream& operator << (ostream& out, const string& s){for (auto ch : s){out  << ch;}return out;}istream& operator >> (istream& in,  string& s){s.clear();char ch = in.get();char buff[128];size_t i = 0;while (ch != ' ' && ch != '\n'){buff[i++] = ch;if (i == 127){buff[127] = '\0';s += buff;i = 0;}	ch = in.get();}if (i != 0){buff[i] = '\0';s += buff;}return in;}

Ⅳ. 迭代器实现

这里只是实现了正向迭代器的实现

		typedef char* iterator;typedef const char* const_iterator;iterator begin(){return _str;}iterator end(){return _str + _size;}const_iterator begin() const {return _str;}const_iterator end() const{return _str + _size;}

到这本篇博客的内容就到此结束了。
如果觉得本篇博客内容对你有所帮助的话,可以点赞,收藏,顺便关注一下!
如果文章内容有错误,欢迎在评论区指正

在这里插入图片描述

http://www.lryc.cn/news/62089.html

相关文章:

  • 耐腐蚀高速电动针阀在半导体硅片清洗机化学药液流量控制中的应用
  • 助力工业物联网,工业大数据之ODS层及DWD层建表语法【七】
  • Windows环境下C++ 安装OpenSSL库 源码编译及使用(VS2019)
  • TensorFlow高阶API和低阶API
  • 强训之【参数解析和跳石板】
  • Redis队列Stream、Redis多线程详解(三)
  • MySQL统计函数count详解
  • 实验04:图像压缩(DP算法)
  • 4.19--面试系列之真题版本--redis出现大key怎么解决?Redis 大 Key 对持久化有什么影响?
  • 新手在家做自媒体要如何起步?
  • 易基因:禾本科植物群落的病毒组丰度/组成与人为管理/植物多样性变化的相关性 | 宏病毒组
  • 华为OD机试——对称美学(通过率只有8.51%???)
  • 【三十天精通Vue 3】第十六天 Vue 3 的虚拟 DOM 原理详解
  • Arduino ESP8266通过udp获取时间以及同步本地时间方法
  • c/c++:char*定义常量字符串,strcmp()函数,strcpy()函数,寻找指定字符,字符串去空格
  • 2023年6月DAMA-CDGA/CDGP数据治理认证考试可报名地区公布
  • UDS的0x19服务介绍
  • QinQ技术与Portal技术
  • Vue-自定义表单验证(rule,value,callback)详细使用
  • 港联证券|TMT板块全线退潮,这些个股获主力逆市抢筹
  • WPF学习
  • C#使用WebDriver模拟浏览器操作WEB页面
  • 正则表达式 - 简单模式匹配
  • 银行数字化转型导师坚鹏:银行数字化转型培训方案
  • 多维时序 | MATLAB实现BO-CNN-LSTM贝叶斯优化卷积神经网络-长短期记忆网络多变量时间序列预测
  • Shell知识点(一)
  • mysql 索引失效、联合索引失效场景和举例
  • 快速将PDF转换为图片:使用在线转换器的步骤
  • 什么是gpt一4-如何用上gpt-4
  • Docker 相关概念