自定義簡易string類c++primer13.44
標頭檔案
#pragma warning(disable:4996) //可參考上一篇解決c4996問題的部落格
#include<iostream>
#include<memory>
#include<algorithm>
#include<utility>
class String {
public:
String() {
elements = nullptr;
first_free = nullptr;
}
String(char *c) { //接受c風格的字串,c指向字串第一個字元
auto c1 = const_cast<char *>(c);
while (*c1) {
++c1;
}
auto p = alloc_n_copy(c, c1);
elements = p.first;
first_free = p.second;
}
String(const String& s) {
auto p = alloc_n_copy(s.elements, s.first_free);
elements = p.first;
first_free = p.second;
}
String &operator=(const String& s) {
auto p = alloc_n_copy(s.elements, s.first_free);
free();
elements = p.first;
first_free = p.second;
}
~String() {
free();
}
void show() {
auto p = elements;
while (p != first_free) {
std::cout << *p;
++p;
}
std::cout << std::endl;
}
size_t size() { return first_free - elements; }
String &operator+(String& s) {
auto p = alloc.allocate(this->size() + s.size());
//註釋部分為拷貝實現
/*auto dataMid = std::uninitialized_copy(this->elements, this->first_free, p);
auto dataEnd = std::uninitialized_copy(s.elements, s.first_free, dataMid);
this->free();
this->elements = p;
this->first_free = dataEnd;*/
//下面採用了移動建構函式std::move,節省了拷貝開銷
auto dest = p; //指向新陣列中下一個空閒位置
auto elem = this->elements; //指向就陣列中下一個元素
for (size_t i = 0; i != this->size(); ++i) {
alloc.construct(dest++, std::move(*elem++));
}
elem = s.elements;
for (size_t i = 0; i != s.size(); ++i) {
alloc.construct(dest++, std::move(*elem++));
}
free();
this->elements = p;
this->first_free = dest;
return *this;
}
private:
char *elements; //指向字串首字元
char *first_free; //指向字串最後一個字元的後一個位置
static std::allocator<char> alloc; //類內靜態成員要在類外進行定義初始化否則會出現LNK2001error
static std::allocator<char> initalloc() {
std::allocator<char> allo;
allo.allocate(1);
return allo;
}
std::pair<char*, char*> alloc_n_copy(const char*, const char*);
void free();
};
std::allocator<char> String::alloc = initalloc();
std::pair<char*, char*> String::alloc_n_copy(const char* c1, const char* c2) {
auto dataBeg = alloc.allocate(c2 - c1);
auto dataEnd = std::uninitialized_copy(c1, c2, dataBeg);
return std::make_pair(dataBeg, dataEnd);
}
void String::free() {
if (elements) {
std::for_each(elements, first_free, [this](char &rhs) {alloc.destroy(&rhs); });
alloc.deallocate(elements, first_free - elements);
}
}
主函式
#include<iostream>
#include"classString.h"
using namespace std;
int main() {
String s("dasdsad11111");
s.show();
String s1(s);
s1.show();
String s2 = s;
s2.show();
cout << s2.size() << endl;
s1 + s2;
s1.show();
return 0;
}
相關文章
- springcloud之自定義簡易消費服務元件SpringGCCloud元件
- iOS自定義控制元件:簡易下拉控制元件iOS控制元件
- 自定義異常類
- 自定義實現Complex類
- Python如何自定義元類Python
- 直播系統原始碼,簡易的自定義確認彈框AlertDialog原始碼
- 短視訊程式開發,簡易的自定義確認彈框AlertDialog
- Django(62)自定義認證類Django
- 易優cms模板在哪自定義表單
- Laravel自定義Make命令生成Service類Laravel
- String類
- SwiftUI 簡明教程之自定義 ModifierSwiftUI
- 【JAVA】自定義類載入器實現類隔離Java
- C++:使自定義類支援迭代器C++
- 前端自定義類事件回撥封裝前端事件封裝
- PHP 自定義session儲存 FILE 方式類PHPSession
- JAVA集合類簡要筆記 - 內部類 包裝類 Object類 String類 BigDecimal類 system類Java筆記ObjectDecimal
- Java String類Java
- 自定義類載入器驗證類載入機制
- Android 入門(三)簡單自定義 ViewAndroidView
- JSP自定義標籤就是如此簡單JS
- python中什麼時候使用自定義類Python
- 類載入流程,類載入機制及自定義類載入器
- 併發程式設計:自定義併發類:自定義非同步流(釋出與訂閱)程式設計非同步
- Android 最簡單的自定義MenuItem之一AndroidUI
- Android 最簡單的自定義Dialog之一Android
- 簡單的自定義表單控制元件控制元件
- 04_String類
- Java使用類-StringJava
- String類的使用
- pytorch載入語音類自定義資料集PyTorch
- tensorflow2.0 自定義類模組列印問題
- SpringBoot應用使用自定義的ApplicationContext實現類Spring BootAPPContext
- 使用 Laravel Resource 類時自定義分頁資訊Laravel
- IDEA自定義類註釋和方法註釋(自定義groovyScript方法實現多行引數註釋)Idea
- 5.Hibernate工具類的簡易封裝封裝
- WPF自定義Panel:讓拖拽變得更簡單
- flutter-簡單實現找妹子自定義viewFlutterView