MyString:string类的模拟实现 1

news2024/12/16 21:28:08

MyString:string类的模拟实现

前言:

为了区分标准库中的string,避免编译冲突,使用命名空间 MyString。

namespace MyString
{
    class string
    {
     private:
        char* _str;
        size_t _size;
        size_t _capacity;
        
        const static size_t npos = -1;// C++标准库支持的特殊用法
    };

在这里插入图片描述

以下都在 MyString 内实现!

一、构造函数,析构函数,拷贝构造

1.1 构造函数

标准库中,构造string类的常见写法:

string s1; // 1
string s2("hello world"); // 2
public:
	string()
        :_str(new char[1])// 给一个字节的空间作为标识
        ,_size(0)
        ,_capacity(0)
    {
        _str[_size] = '\0';
    }
    
    string(const char* str)
    {
        _size = strlen(str);
        _capacity = _size;
        _str = new char[_capacity + 1];// 多给一个空间,存'\0'
        strcpy(_str, str);
    }

实际上,对第二个构造函数的参数进行缺省,可以实现两种写法的完美统一。

    string(const char* str = "") // 字符串末尾有隐藏的'\0',不需要我们在缺省值加上'\0'
    {
        _size = strlen(str);
        _capacity = _size;
        _str = new char[_capacity + 1];
        strcpy(_str, str);
    }
1.2 析构函数
public:
	~string()
    {
        delete[] _str;
        _str = nullptr;
        _size = _capacity = 0;
	}
1.3 拷贝构造(重点)

string类的拷贝构造需要实现深拷贝否则会造成资源的二次释放

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

二、迭代器

public:
	typedef char* iterator;
	typedf 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;
	}

范围for 本质是对迭代器的“傻瓜式”替换,一旦对 begin() end() 的函数名做修改,则无法调用,如:begin() ——> Begin() 。

三、reserve() 与 尾插(重点)

3.1 reserve()

【1】 reserve() 是对 _capacity 进行操作 (不对 _str 操作),而 _capacity 只计算有效字符个数不包括字符串末尾的 ‘\0’

【2】 在设计 reserve() 时,要考虑多开一个空间,用于存 ‘\0’ ;要对 _capacity 校正

【3】 在使用 reserve() 进行扩容时,只需要考虑 有效字符个数 即可。

public:
	void reserve(size_t n)
    {
        if (n > _capacity)
        {
            char* tmp = new char[n + 1];// 
            strcpy(tmp, _str);
            delete[] _str;
            _str = tmp;
            _capacity = n;
		}
    }
  • n > _capacity 时,才需要调整
  • char* tmp = new char[n + 1] 多开一个空间,用于存 ‘\0’ 。
3.2 尾插一个字符:push_back()
public:
	void push_back(const char ch)
    {
        if (_size == _capacity)
        {
            size_t newCapacity = _capacity == 0 ? 4 : 2 * _capacity;
            reserve(newCapacity);
            // _capacity = newCapacity;
            // reserve中 已经对 _capacity 做过调整了
		}
        _str[_size] = ch;
        ++_size;
        _str[_size] = '\0';
	}
  • 插入字符后,应在字符串末尾加上 ‘\0’否则通过 _str 访问字符串元素时会出现异常
3.3 尾插字符串:append()
public:
	void append(const char* str)
    {
        int len = strlen(str);
        if (_size + len > _capacity)
        {
            reserve(_size + len);
            // reserve(_size + len + 1); // reserve中 已考虑在字符串末尾加上'\0'
		}
        strcpy(_str + _size, str);// str 末尾有隐藏的 '\0'
        _size += len;
	}
  • str 末尾有隐藏的 ‘\0’
3.4 += 重载
  • s1 += “x”;
public:
	string& operator+=(const char ch)
    {
        push_back(ch);
        return *this;
	}
  • s1 += “xxxx”;
public:
	string& operator+=(const char* str)
    {
        append(str);
        return *this;
    }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1299376.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

解锁MySQL的威力:针对常见问题的快速解决指南

数据库和表的创建 创建数据库: CREATE DATABASE IF NOT EXISTS MyDatabase; USE MyDatabase;案例: 想象您要开始一个博客项目。首先,您需要一个地方来存储所有的文章和用户信息。上述命令帮助您创建了这样一个存储空间,名为MyDa…

人力资源服务展示网站作用有哪些

就业劳务问题往往是不少人群关注的问题,每个城市都聚集着大量求业者,而人力资源管理公司每年也会新增不少,对求业者来说,通过人力资源公司可以快速便捷的找到所需工作,而对公司来说,市场大量用户可以带来收…

python/matlab图像去雾/去雨综述

图像去雾和去雨是计算机视觉领域的两个重要任务,旨在提高图像质量和可视化效果。本文将综述图像去雾和去雨的算法、理论以及相关项目代码示例。 一、图像去雾算法 基于暗通道先验的方法: 这是广泛应用于图像去雾的经典算法之一。该方法基于一个观察&…

Aloha 机械臂的学习记录2——AWE:AWE + ACT

继续下一个阶段: Train policy python act/imitate_episodes.py \ --task_name [TASK] \ --ckpt_dir data/outputs/act_ckpt/[TASK]_waypoint \ --policy_class ACT --kl_weight 10 --chunk_size 50 --hidden_dim 512 --batch_size 8 --dim_feedforward 3200 \ --n…

操作系统学习笔记---内存管理

目录 概念 功能 内存空间的分配和回收 地址转换 逻辑地址(相对地址) 物理地址(绝对地址) 内存空间的扩充 内存共享 存储保护 方式 源程序变为可执行程序步骤 链接方式 装入方式 覆盖 交换 连续分配管理方式 单一连…

self-attention|李宏毅机器学习21年

来源:https://www.bilibili.com/video/BV1Bb4y1L7FT?p1&vd_sourcef66cebc7ed6819c67fca9b4fa3785d39 文章目录 引言self-attention运作机制b1是如何产生的怎么求关联性数值 α \alpha α 从矩阵乘法的角度再来一次从A得到Q、K、V从Q、K得到 α \alpha α矩阵由…

IT行业最被低估的六项技术,再加上一项尚未消亡的技术

2023年,生成式人工智能——更具体地说是ChatGPT——吸引了业界的广泛关注,深得董事会、首席执行官和其他高管的一致赞赏(也不乏害怕情绪)。当然,他们的热情是有道理的,多项研究发现,人工智能正在…

Nginx缓存及HTTPS配置小记

缓存基础 缓存分类 某些场景下,Nginx需要通过worker到上有服务中获取数据并将结果响应给客户端,在高并发场景下,我们完全可以将这些数据视为热点数据,并将其缓存到Nginx服务上。 客户端缓存:将缓存数据放到客户端。 …

Linux和Windows环境下如何使用gitee?

1. Linux 1.1 创建远程仓库 1.2 安装git sudo yum install -y git 1.3 克隆远程仓库到本地 git clone 地址 1.4 将文件添加到git的暂存区(git三板斧之add) git add 文件名 # 将指定文件添加到git的暂存区 git add . # 添加新文件和修改过的…

DTCC2023大会-DBdoctor-基于eBPF观测数据库-附所有PPT下载链接

DTCC2023大会-DBdoctor-基于eBPF观测数据库-附所有PPT下载链接 8月16日—18日,第14届中国数据库技术大会(DTCC-2023)在北京国际会议中心举行。聚好看在大会上首次发布基于eBPF观测数据库性能的产品DBdoctor,受到了业界广泛的关注。近期几位业内同仁过来要大会的PPT…

NLP项目实战01--电影评论分类

介绍: 欢迎来到本篇文章!在这里,我们将探讨一个常见而重要的自然语言处理任务——文本分类。具体而言,我们将关注情感分析任务,即通过分析电影评论的情感来判断评论是正面的、负面的。 展示: 训练展示如下…

消息队列使用指南

介绍 消息队列是一种常用的应用程序间通信方法,可以用来在不同应用程序或组件之间传递数据或消息。消息队列就像一个缓冲区,接收来自发送方的消息,并存储在队列中,等待接收方从队列中取出并处理。 在分布式系统中,消…

Git的安装以及SSH配置

前言 近期工作需要,所以版本管理工具要用到Git,某些操作需要ssh进行操作,在某次操作中遇到:git bash报错:Permission denied, please try again。经排查是ssh没有配置我的key,所以就借着这篇文章整理了一下…

【小白专用】使用PHP创建和操作MySQL数据库,数据表

php数据库操作 php连接mysql数据库 <?php $hostlocalhost; // 数据库主机名 $username"root"; // 数据库用户名 $password"al6"; // 数据库密码 $dbname"mysql"; // 数据库名 $connIDmysqli_connect($host,$username,$password,$dbn…

Electron[4] Electron最简单的打包实践

1 背景 前面三篇已经完成通过Electron搭建的最简单的HelloWorld应用了&#xff0c;虽然这个应用还没添加任何实质的功能&#xff0c;但是用来作为打包的案例&#xff0c;足矣。下面再分享下通过Electron-forge来将应用打包成安装包。 2 依赖 在Electron[2] Electron使用准备…

AXURE地图获取方法

AXURE地图截取地址 https://axhub.im/maps/ 1、点击上方地图或筛选所需地区的地图&#xff0c;点击复制到 Axure 按钮&#xff0c;到 Axure 粘贴就可以了 2、复制到 Axure 后&#xff0c;转化为 svg 图形&#xff0c;就可以随意更改尺寸/颜色/边框&#xff0c;具体操作如下&am…

RocketMQ-源码架构二

梳理一些比较完整&#xff0c;比较复杂的业务线 消息持久化设计 RocketMQ的持久化文件结构 消息持久化也就是将内存中的消息写入到本地磁盘的过程。而磁盘IO操作通常是一个很耗性能&#xff0c;很慢的操作&#xff0c;所以&#xff0c;对消息持久化机制的设计&#xff0c;是…

使用Java8的Stream流的Collectors.toMap来生成Map结构

问题描述 在日常开发中总会有这样的代码&#xff0c;将一个List转为Map集合&#xff0c;使用其中的某个属性为key&#xff0c;某个属性为value。 常规实现 public class CollectorsToMapDemo {DataNoArgsConstructorAllArgsConstructorpublic static class Student {private…

基于YOLOv8深度学习的舰船目标分类检测系统【python源码+Pyqt5界面+数据集+训练代码】目标检测、深度学习实战

《博主简介》 小伙伴们好&#xff0c;我是阿旭。专注于人工智能、AIGC、python、计算机视觉相关分享研究。 ✌更多学习资源&#xff0c;可关注公-仲-hao:【阿旭算法与机器学习】&#xff0c;共同学习交流~ &#x1f44d;感谢小伙伴们点赞、关注&#xff01; 《------往期经典推…

【pycharm】Pycharm中进行Git版本控制

本篇文章主要记录一下自己在pycharm上使用git的操作&#xff0c;一个新项目如何使用git进行版本控制。 文章使用的pycharm版本PyCharm Community Edition 2017.2.4&#xff0c;远程仓库为https://gitee.com/ 1.配置Git&#xff08;File>Settings&#xff09; 2.去Gitee创建…