MySrting的模拟实现

1.MyString 分文件实现

一、分文件核心规则

.h 头文件:只写声明(类、函数、变量),加头文件保护,禁止写实现、禁止using namespace std。.cpp 源文件:只写实现,包含头文件,成员函数加类名::,静态成员在此定义。

声明与实现函数签名必须完全一致(参数、const、返回值)。

二、内存管理(重中之重)

必须实现深拷贝三大件:拷贝构造、赋值重载、析构函数,杜绝浅拷贝崩溃。

赋值重载用拷贝交换法,简洁安全。

扩容用reserve,默认2 倍扩容,减少内存分配。

字符串始终以\0结尾。

三、函数实现要点

const函数:不修改对象的接口必须加const。

默认参数:仅在头文件声明中写。

迭代器:用原生指针实现,区分普通 /const 版本。

运算符:+=做成员函数,+/==/<<做全局函数。

四、高频避坑

越界访问:用assert校验下标。

头文件缺失:strlen→<cstring>,isspace→<cctype>。

内存匹配:new\[\]必须搭配delete\[\]。

编译:所有.cpp文件必须一起编译链接

2.程序实现

1.h文件
cpp 复制代码
#ifndef MYSTRING_H
#define MYSTRING_H

#include <iostream>
#include <cstring>
#include <cassert>
#include <algorithm>

// 头文件严禁写 using namespace std!!!
class MyString
{
public:
    typedef char* iterator;
    typedef const char* const_iterator;

    // 静态常量声明
    const static std::size_t npos;

    // 构造/析构/拷贝
    MyString();
    MyString(const char* s);
    MyString(const MyString& s);
    MyString& operator=(MyString s);
    ~MyString();
    void Swap(MyString& s);

    // 迭代器
    iterator begin();
    iterator end();
    const_iterator begin() const;
    const_iterator end() const;

    // 容量
    std::size_t size() const;
    std::size_t capacity() const;
    bool empty() const;
    void clear();
    void reserve(std::size_t n);
    void resize(std::size_t n, char ch = '\0');

    // 访问
    char& operator[](std::size_t pos);
    const char& operator[](std::size_t pos) const;
    const char* c_str() const;

    // 修改
    void push_back(char ch);
    void append(const char* s);
    MyString& operator+=(char ch);
    MyString& operator+=(const char* s);
    MyString& operator+=(const MyString& s);
    void insert(std::size_t pos, char ch);
    void erase(std::size_t pos, std::size_t len = npos);

    // 查找
    std::size_t find(char ch, std::size_t pos = 0) const;
    std::size_t find(const char* s, std::size_t pos = 0) const;

private:
    char* _str;
    std::size_t _size;
    std::size_t _capacity;
};

// 全局运算符声明
MyString operator+(const MyString& s1, const MyString& s2);
bool operator==(const MyString& s1, const MyString& s2);
bool operator!=(const MyString& s1, const MyString& s2);
bool operator<(const MyString& s1, const MyString& s2);
std::ostream& operator<<(std::ostream& out, const MyString& s);
std::istream& operator>>(std::istream& in, MyString& s);

#endif
2.cpp文件
cpp 复制代码
#define _CRT_SECURE_NO_WARNINGS 1
#include "MyString.h"
#include <cctype>   // 修复:isspace() 必须包含的头文件!

using namespace std;

// 静态常量定义
const size_t MyString::npos = -1;

// 构造/析构
MyString::MyString()
    : _str(new char[1] {'\0'})
    , _size(0)
    , _capacity(0)
{
}

MyString::MyString(const char* s)
{
    _size = strlen(s);
    _capacity = _size;
    _str = new char[_capacity + 1];
    strcpy(_str, s);
}

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

MyString& MyString::operator=(MyString s)
{
    Swap(s);
    return *this;
}

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

void MyString::Swap(MyString& s)
{
    swap(_str, s._str);
    swap(_size, s._size);
    swap(_capacity, s._capacity);
}

// 迭代器
MyString::iterator MyString::begin() { return _str; }
MyString::iterator MyString::end() { return _str + _size; }
MyString::const_iterator MyString::begin() const { return _str; }
MyString::const_iterator MyString::end() const { return _str + _size; }

// 容量
size_t MyString::size() const { return _size; }
size_t MyString::capacity() const { return _capacity; }
bool MyString::empty() const { return _size == 0; }

void MyString::clear()
{
    _size = 0;
    _str[0] = '\0';
}

void MyString::reserve(size_t n)
{
    if (n > _capacity)
    {
        char* tmp = new char[n + 1];
        strcpy(tmp, _str);
        delete[] _str;
        _str = tmp;
        _capacity = n;
    }
}

void MyString::resize(size_t n, char ch)
{
    if (n <= _size)
    {
        _size = n;
        _str[_size] = '\0';
    }
    else
    {
        reserve(n);
        for (size_t i = _size; i < n; ++i)
            _str[i] = ch;
        _size = n;
        _str[_size] = '\0';
    }
}

// 元素访问
char& MyString::operator[](size_t pos)
{
    assert(pos < _size);
    return _str[pos];
}

const char& MyString::operator[](size_t pos) const
{
    assert(pos < _size);
    return _str[pos];
}

const char* MyString::c_str() const { return _str; }

// 修改操作
void MyString::push_back(char ch)
{
    if (_size == _capacity)
        reserve(_capacity == 0 ? 4 : _capacity * 2);

    _str[_size++] = ch;
    _str[_size] = '\0';
}

void MyString::append(const char* s)
{
    size_t len = strlen(s);
    if (_size + len > _capacity)
        reserve(_size + len);

    strcpy(_str + _size, s);
    _size += len;
}

MyString& MyString::operator+=(char ch) { push_back(ch); return *this; }
MyString& MyString::operator+=(const char* s) { append(s); return *this; }
MyString& MyString::operator+=(const MyString& s) { append(s._str); return *this; }

void MyString::insert(size_t pos, char ch)
{
    assert(pos <= _size);
    if (_size == _capacity)
        reserve(_capacity == 0 ? 4 : _capacity * 2);

    for (size_t i = _size; i > pos; --i)
        _str[i] = _str[i - 1];

    _str[pos] = ch;
    _size++;
    _str[_size] = '\0';
}

void MyString::erase(size_t pos, size_t len)
{
    assert(pos < _size);
    if (len == npos || pos + len >= _size)
    {
        _str[pos] = '\0';
        _size = pos;
    }
    else
    {
        strcpy(_str + pos, _str + pos + len);
        _size -= len;
    }
}

// 查找
size_t MyString::find(char ch, size_t pos) const
{
    assert(pos <= _size);
    for (size_t i = pos; i < _size; ++i)
        if (_str[i] == ch) return i;
    return npos;
}

size_t MyString::find(const char* s, size_t pos) const
{
    assert(pos <= _size);
    const char* p = strstr(_str + pos, s);
    return p ? p - _str : npos;
}

// 全局运算符实现
MyString operator+(const MyString& s1, const MyString& s2)
{
    MyString tmp = s1;
    tmp += s2;
    return tmp;
}

bool operator==(const MyString& s1, const MyString& s2)
{
    return strcmp(s1.c_str(), s2.c_str()) == 0;
}
bool operator!=(const MyString& s1, const MyString& s2)
{
    return !(s1 == s2);
}
bool operator<(const MyString& s1, const MyString& s2)
{
    return strcmp(s1.c_str(), s2.c_str()) < 0;
}

ostream& operator<<(ostream& out, const MyString& s)
{
    for (size_t i = 0; i < s.size(); ++i)
        out << s[i];
    return out;
}

istream& operator>>(istream& in, MyString& s)
{
    s.clear();
    char ch;
    while (in.get(ch) && !isspace(ch))
        s += ch;
    return in;
}
3.mian文件
cpp 复制代码
#include "MyString.h"
using namespace std;

int main()
{
    MyString s1;
    MyString s2("hello world");
    MyString s3 = s2;
    MyString s4 = s2;

    cout << "s1: " << s1 << endl;
    cout << "s2: " << s2 << endl;
    cout << "s3: " << s3 << endl;

    s2[0] = 'H';
    s2 += "!!!";
    cout << "\n修改后s2: " << s2 << endl;

    s2.insert(5, ' ');
    s2.erase(5, 1);
    cout << "插入删除后: " << s2 << endl;

    size_t pos = s2.find('w');
    if (pos != MyString::npos)
        cout << "字符w位置: " << pos << endl;

    return 0;
}

谢谢

相关推荐
鹏晨互联15 小时前
《Kotlin高阶函数完全指南:从入门到精通的15个核心函数》
android·开发语言·kotlin
周杰伦fans15 小时前
DeepSeek 智能效果全景展示
算法
Rabitebla15 小时前
C++ 继承详解(下):默认成员函数、虚继承底层与设计取舍
c语言·开发语言·数据结构·c++·算法·leetcode
枫叶丹415 小时前
【HarmonyOS 6.0】Live View Kit深度解析:实况胶囊尾部图标的设计哲学与实现全流程
开发语言·华为·harmonyos
爱喝水的鱼丶16 小时前
SAP-ABAP:条件判断与循环控制语句(7篇)第七篇:性能优化:条件与循环代码的常见性能瓶颈与优化方案
学习·算法·性能优化·sap·abap
吃好睡好便好21 小时前
提取矩阵某一行或某一列元素
开发语言·人工智能·线性代数·算法·matlab·矩阵
deepin_sir1 天前
10 - 函数
开发语言·python
z落落1 天前
C#String字符串
开发语言·c#·php
wljy11 天前
二、进制状态转换
linux·运维·服务器·c语言·c++