引子:我們學習了c++中的string類,那我們能不能像以前數據結構一樣自己實現string類呢?以下是cplusplus下的string類,我們參考參考!
廢話不多說,直接代碼實現:(注意函數之間的復用!)
#define _CRT_SECURE_NO_WARNINGS 1
#pragma once
#include<iostream>
#include<assert.h>
using namespace std;
//一般在類外進行靜態區變量賦值
const static size_t npos = -1;
//本string簡單實現,代碼量小,故直接寫在聲明中
namespace bit
{
?? ?class string
?? ?{
?? ?public:
?? ??? ?//采用typedef 讓iterator保持接口的一致性
?? ??? ?//iterator底層是模版template
?? ??? ?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;
?? ??? ?}
?? ??? ?//構造函數
?? ??? ?string(const char* str = "")
?? ??? ??? ?:_size(strlen(str))
?? ??? ?{
?? ??? ??? ?_str = new char[_size + 1];//為深拷貝,因為如果淺拷貝的話,共用一塊空間,那結果可想而知
?? ??? ??? ?_capacity = _size;
?? ??? ??? ?strcpy(_str, str);//注意char * strcpy ( char * destination, const char * source );
?? ??? ?}
?? ??? ?//拷貝構造,可以隱式類型賦值
?? ??? ?string(const string& s)
?? ??? ?{
?? ??? ??? ?_str = new char[s._capacity + 1];
?? ??? ??? ?strcpy(_str, s._str);
?? ??? ??? ?_size = s._size;
?? ??? ??? ?_capacity = s._capacity;
?? ??? ?}
?? ??? ?string& operator=(const string& s)
?? ??? ?{
?? ??? ??? ?if (this != &s)//排除等于自身的情況
?? ??? ??? ?{
?? ??? ??? ??? ?char* tmp = new char[s._capacity + 1];
?? ??? ??? ??? ?strcpy(tmp, s._str);
?? ??? ??? ??? ?delete[]_str;//只析構_str上的資源
?? ??? ??? ??? ?_str = tmp;
?? ??? ??? ??? ?_size = s._size;
?? ??? ??? ??? ?_capacity = s._capacity;
?? ??? ??? ?}
?? ??? ??? ?return *this;
?? ??? ?}
?? ??? ?~string()
?? ??? ?{
?? ??? ??? ?delete[]_str;
?? ??? ??? ?_str = nullptr;
?? ??? ??? ?_size = _capacity = 0;
?? ??? ?}
?? ??? ?const char* c_str() const
?? ??? ?{
?? ??? ??? ?return _str;
?? ??? ?}
?? ??? ?size_t size() const
?? ??? ?{
?? ??? ??? ?return _size;
?? ??? ?}
?? ??? ?char& operator[](size_t pos)
?? ??? ?{
?? ??? ??? ?assert(pos < _size);
?? ??? ??? ?return _str[pos];
?? ??? ?}
?? ??? ?const char& operator[](size_t pos) const
?? ??? ?{
?? ??? ??? ?assert(pos < _size);
?? ??? ??? ?return _str[pos];
?? ??? ?}
?? ??? ?void reserve(size_t n)
?? ??? ?{
?? ??? ??? ?if (n > _capacity)
?? ??? ??? ?{
?? ??? ??? ??? ?char* tmp = new char[n + 1];
?? ??? ??? ??? ?strcpy(tmp, _str);
?? ??? ??? ??? ?delete[] _str;
?? ??? ??? ??? ?_str = tmp;
?? ??? ??? ??? ?_capacity = n;
?? ??? ??? ?}
?? ??? ?}
?? ??? ?void insert(size_t pos, char ch)
?? ??? ?{
?? ??? ??? ?assert(pos <= _size);
?? ??? ??? ?if (_size == _capacity)
?? ??? ??? ?{
?? ??? ??? ??? ?size_t newcapacity = _capacity == 0 ? 4 : _capacity * 2;
?? ??? ??? ??? ?reserve(newcapacity);
?? ??? ??? ?}
?? ??? ??? ?size_t end = _size + 1;
?? ??? ??? ?while (end > pos)
?? ??? ??? ?{
?? ??? ??? ??? ?_str[end] = _str[end - 1];
?? ??? ??? ??? ?--end;
?? ??? ??? ?}
?? ??? ??? ?_str[pos] = ch;
?? ??? ??? ?++_size;
?? ??? ?}
?? ??? ?void insert(size_t pos, const char* str)
?? ??? ?{
?? ??? ??? ?assert(pos <= _size);
?? ??? ??? ?size_t len = strlen(str);
?? ??? ??? ?if (_size + len > _capacity)
?? ??? ??? ?{
?? ??? ??? ??? ?reserve(_size + len);
?? ??? ??? ?}
?? ??? ??? ?size_t end = _size;
?? ??? ??? ?//注意pos=0時,對應的值為size_t類型,要int轉
?? ??? ??? ?while (end > (int)pos)
?? ??? ??? ?{
?? ??? ??? ??? ?_str[end+len] = _str[end];
?? ??? ??? ??? ?--end;
?? ??? ??? ?}
?? ??? ??? ?memcpy(_str + pos, str, len);//void * memcpy ( void * destination, const void * source, size_t num );
?? ??? ??? ?_size += len;
?? ??? ?}
?? ??? ?void push_back(char ch)
?? ??? ?{
?? ??? ??? ?insert(_size, ch);
?? ??? ?}
?? ??? ?void append(const char* str)
?? ??? ?{
?? ??? ??? ?insert(_size, str);
?? ??? ?}
?? ??? ?string& operator+=(char ch)
?? ??? ?{
?? ??? ??? ?push_back(ch);
?? ??? ??? ?return *this;
?? ??? ?}
?? ??? ?string& operator+=(const char* str)
?? ??? ?{
?? ??? ??? ?append(str);
?? ??? ??? ?return *this;
?? ??? ?}
?? ??? ?void erase(size_t pos = 0, size_t len = npos)
?? ??? ?{
?? ??? ??? ?assert(pos < _size);
?? ??? ??? ?// len大于前面字符個數時,有多少刪多少
?? ??? ??? ?if (len >= _size - pos)
?? ??? ??? ?{
?? ??? ??? ??? ?_str[pos] = '\0';
?? ??? ??? ??? ?_size = pos;
?? ??? ??? ?}
?? ??? ??? ?else
?? ??? ??? ?{
?? ??? ??? ??? ?strcpy(_str + pos, _str + pos + len);
?? ??? ??? ??? ?_size -= len;
?? ??? ??? ?}
?? ??? ?}
?? ??? ?size_t find(char ch, size_t pos = 0)
?? ??? ?{
?? ??? ??? ?for (size_t i = pos; i < _size; i++)
?? ??? ??? ?{
?? ??? ??? ??? ?if (_str[i] == ch)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?return i;
?? ??? ??? ??? ?}
?? ??? ??? ?}
?? ??? ??? ?return npos;
?? ??? ?}
?? ??? ?size_t find(const char* str, size_t pos = 0)
?? ??? ?{
?? ??? ??? ?char* p = strstr(_str + pos, str);//char * strstr (char * str1, const char * str2 );
?? ??? ??? ?return ?p - _str;
?? ??? ?}
?? ??? ?void swap(string& s)
?? ??? ?{
?? ??? ??? ?std::swap(_str, s._str);
?? ??? ??? ?std::swap(_size, s._size);
?? ??? ??? ?std::swap(_capacity, s._capacity);
?? ??? ?}
?? ??? ?string substr(size_t pos = 0, size_t len = npos)
?? ??? ?{
?? ??? ??? ?// len大于后面剩余字符,有多少取多少
?? ??? ??? ?if (len > _size - pos)
?? ??? ??? ?{
?? ??? ??? ??? ?string sub(_str + pos);
?? ??? ??? ??? ?return sub;
?? ??? ??? ?}
?? ??? ??? ?else
?? ??? ??? ?{
?? ??? ??? ??? ?string sub;
?? ??? ??? ??? ?sub.reserve(len);
?? ??? ??? ??? ?for (size_t i = 0; i < len; i++)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?sub += _str[pos + i];
?? ??? ??? ??? ?}
?? ??? ??? ??? ?return sub;
?? ??? ??? ?}
?? ??? ?}
?? ??? ?bool operator<(const string& s) const
?? ??? ?{
?? ??? ??? ?return strcmp(_str, s._str) < 0;
?? ??? ?}
?? ??? ?bool operator>(const string& s) const
?? ??? ?{
?? ??? ??? ?return !(*this <= s);
?? ??? ?}
?? ??? ?bool operator<=(const string& s) const
?? ??? ?{
?? ??? ??? ?return *this < s || *this == s;
?? ??? ?}
?? ??? ?bool operator>=(const string& s) const
?? ??? ?{
?? ??? ??? ?return !(*this < s);
?? ??? ?}
?? ??? ?bool operator==(const string& s) const
?? ??? ?{
?? ??? ??? ?return strcmp(_str, s._str) == 0;
?? ??? ?}
?? ??? ?bool operator!=(const string& s) const
?? ??? ?{
?? ??? ??? ?return !(*this == s);
?? ??? ?}
?? ??? ?void clear()
?? ??? ?{
?? ??? ??? ?_str[0] = '\0';
?? ??? ??? ?_size = 0;
?? ??? ?}
?? ?private:
?? ??? ?// char _buff[16];
?? ??? ?char* _str;
?? ??? ?size_t _size;
?? ??? ?size_t _capacity;
?? ??? ?const static size_t npos;
?? ?};
?? ?istream& operator>> (istream& is, string& str)
?? ?{
?? ??? ?str.clear();
?? ??? ?char ch = is.get();
?? ??? ?while (ch != ' ' && ch != '\n')
?? ??? ?{
?? ??? ??? ?str += ch;
?? ??? ??? ?ch = is.get();
?? ??? ?}
?? ??? ?return is;
?? ?}
?? ?ostream& operator<< (ostream& os, const string& str)
?? ?{
?? ??? ?for (size_t i = 0; i < str.size(); i++)
?? ??? ?{
?? ??? ??? ?os << str[i];
?? ??? ?}
?? ??? ?return os;
?? ?}
}