#include "../inc/strvec.h"#include <algorithm>#include <iostream>#include <memory>#include <string>#include <tuple>#include <vector>using namespace std;std::allocator<std::string> StrVec::alloc;void StrVec::push_back(const std::string &s){chk_n_alloc();alloc.construct(first_free++, s);}//重新开辟空间void StrVec::reallocate(){string *newdata = nullptr;//数组为空的情况if (elements == nullptr || cap == nullptr || first_free == nullptr){newdata = alloc.allocate(1);// elements和first_free都指向首元素elements = newdata;first_free = newdata;// cap指向数组尾元素的下一个位置。cap = newdata + 1;return;}//不为空则扩充两倍空间newdata = alloc.allocate(size() * 2);//新内存空闲位置auto dest = newdata;//旧内存有效位置auto src = elements;//通过移动操作将旧数据放到新内存中for (size_t i = 0; i != size(); ++i){alloc.construct(dest++, std::move(*src++));}//移动后旧内存数据无效,一定要删除free();//更新数据位置elements = newdata;//更新第一个空闲位置first_free = dest;//更新容量cap = elements + size() * 2;}//释放操作void StrVec::free(){//判断elements是否为空if (elements == nullptr){return;}auto dest = elements;//要先遍历析构每一个对象for (size_t i = 0; i < size(); i++){// destroy会调用每一个元素的析构函数alloc.destroy(dest++);}//再整体回收内存alloc.deallocate(elements, cap - elements);elements = nullptr;cap = nullptr;first_free = nullptr;}// copy指定范围的元素到新的内存中,返回新元素的地址和第一个空闲元素地址的pairstd::pair<std::string *, std::string *> StrVec::alloc_n_copy(const std::string *b, const std::string *e){auto newdata = alloc.allocate(e - b);//将原数据用来初始化新空间auto first_free = uninitialized_copy(b, e, newdata);return {newdata, first_free};}//拷贝构造函数StrVec::StrVec(const StrVec &strtmp){//将形参数据拷贝给自己auto rsp = alloc_n_copy(strtmp.begin(), strtmp.end());//更新elements, cap,first_freeelements = rsp.first;first_free = rsp.second;cap = rsp.second;}//拷贝赋值运算符StrVec &StrVec::operator=(const StrVec &strtmp){cout << "this is copy operator = " << endl;//防止自赋值if (this == &strtmp){return *this;}//将形参数据拷贝给自己auto rsp = alloc_n_copy(strtmp.begin(), strtmp.end());//更新elements, cap,first_freeelements = rsp.first;first_free = rsp.second;cap = rsp.second;}//析构StrVec::~StrVec(){free();}//抛出元素void StrVec::pop_back(std::string &s){if (first_free == nullptr){return;}if (size() == 1){s = *elements;alloc.destroy(elements);first_free = nullptr;elements = nullptr;return;}s = *(--first_free);alloc.destroy(first_free);}void test_strvec_old(){auto str1 = StrVec();str1.push_back("hello zack");StrVec str2(str1);str2.push_back("hello rolin");StrVec str3 = str1;string strtmp;str3.pop_back(strtmp);}void test_strvec(){StrVec v1, v2;//左值赋值v1 = v2;//函数返回的是右值,//右值赋值会调用移动赋值v2 = get_vec_str();}//移动赋值运算符StrVec &StrVec::operator=(StrVec &&src){cout << "this is move operator = " << endl;if (this != &src){//释放自己的空间操作this->free();//接管源对象资源this->elements = src.elements;this->first_free = src.first_free;this->cap = src.cap;//将源对象成员赋值为空src.elements = src.first_free = src.cap = nullptr;}return *this;}StrVec get_vec_str(){return StrVec();}
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。