string的简单实现
#include <string>
#include <iostream>
using namespace std;
/*
* todo
* 1. copy on write
* */
class String {
public:
using size_type = size_t;
using value_type = char;
using pointer = char *;
//有参构造
String(const char *src = nullptr) {
init();
if (nullptr == src) {
return;
}
size_type sz = strlen(src);
rep.Long = false;
add(src, sz);
}
//拷贝
String(const String &s) {
copy(s);
}
//移动
explicit String(String &&s) {
rep = s.rep;
if (s.rep.Long) {
s.init();
}
}
~String() {
destory();
}
//赋值
String &operator=(const String &s) {
destory();
init();
copy(s);
return *this;
}
//赋值
String &operator=(String &&s) noexcept {
destory();
init();
rep = s.rep;
if (s.rep.Long) {
s.init();
}
return *this;
}
//左移运算符重载
friend ostream &operator<<(ostream &os, const String &s) {
if (s.rep.Long) {
os << s.rep.m_l.beg_;
} else {
os << s.rep.m_s.m_data_;
}
return os;
}
String &operator+=(const String &right) {
add(right);
return *this;
}
friend String operator+(const String &left, const String &right);
//输出大小
[[nodiscard]] size_t size() const {
if (rep.Long) {
return rep.m_l.size_;
}
return rep.m_s.size_;
}
[[nodiscard]] pointer c_str() const {
if (rep.Long) {
return rep.m_l.beg_;
} else {
return (pointer) rep.m_s.m_data_;
}
}
private:
void init() {
rep.Long = false;
rep.m_s.size_ = 0;
rep.m_s.m_data_[0] = '\0';
}
void add(const String &s) {
if (s.rep.Long) {
add(s.rep.m_l.beg_, s.rep.m_l.size_);
} else {
add((pointer) s.rep.m_s.m_data_, s.rep.m_s.size_);
}
}
void add(const char *src, int n) {
if (!rep.Long) {
if (!rep.m_s.add(src, n)) {
// 复制原值
m_rep other = this->rep;
rep.Long = true;
int sz = other.m_s.size_;
rep.m_l.init(sz + n + 1);
rep.m_l.add((pointer) other.m_s.m_data_, other.m_s.size_);
}
}
if (rep.Long) {
rep.m_l.add(src, n);
}
}
void destory() {
if (this->rep.Long) {
if (rep.Long) {
rep.m_l.destroy_long();
init();
}
}
}
void copy(const String &str) {
this->rep.Long = str.rep.Long;
if (!str.rep.Long) {
this->rep.m_s.copy(str.rep.m_s);
} else {
add(str.rep.m_l.beg_, str.rep.m_l.size_);
}
}
// 长字符串
class m_long {
public:
pointer beg_;
pointer cap_;
size_type size_;
void destroy_long() {
if (nullptr != beg_) {
delete[] beg_;
beg_ = nullptr;
}
}
void init(size_type n) {
beg_ = new value_type[n];
cap_ = beg_ + n;
size_ = 0;
}
void move(m_long *other) {
beg_ = other->beg_;
cap_ = other->cap_;
size_ = other->size_;
}
void copy(m_long *other) {
for (int i = 0; i < other->size_; i++) {
beg_[i] = other->beg_[i];
}
size_ = other->size_;
}
void enlarge(size_type n) {
size_type room = cap_ - beg_;
if (room < 1024) {
room = room * 2 + n;
} else {
room += n;
}
m_long other;
other.move(this);
this->init(room);
this->copy(&other);
other.destroy_long();
}
void enLargeIfNeed(size_type n) {
if (cap_ - beg_ < n) {
enlarge(n);
}
}
void add(const char *str, size_t n) {
if (nullptr == str || n == 0) {
return;
}
enLargeIfNeed(n);
strncpy(beg_ + size_, str, n);
size_ += n;
beg_[size_] = '\0';
}
};
enum {m_min_cap = (sizeof(m_long) - 1)/sizeof(value_type) > 2 ?
(sizeof(m_long) - 1)/sizeof(value_type) : 2};
// 短字符串
struct m_short {
value_type m_data_[m_min_cap];
unsigned char size_;
void init(size_type n) {
size_ = 0;
}
bool add(const char *str, size_t n) {
if (nullptr == str || n == 0) {
return true;
}
if (size_ + n + 1 > m_min_cap) {
return false;
}
strncpy(m_data_ + size_, str, n);
size_ += n;
m_data_[size_] = '\0';
return true;
}
void copy(const m_short &other) {
size_ = other.size_;
strncpy(this->m_data_, other.m_data_, size_);
this->m_data_[size_] = '\0';
}
};
struct m_rep {
bool Long{};
union {
m_long m_l;
m_short m_s;
};
};
m_rep rep;
};
String operator+(const String &left, const String &right) {
String s;
s.add(left);
s.add(right);
return s;
}
int main() {
String s1("hello world");
cout << s1.size() << " " << s1 << endl;
String s2 = s1;
cout << s2.size() << " "<< s2 << endl;
String s3;
cout << s3.size() << " " << s3 << endl;
String s;
s += "abcasdsdsadsdfsadfa fsdfsadas";
cout << s << endl;
}
输出
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds
c++ string的简单实现x x s x x x x x x x xcxxcadds