C++之模拟实现vector(下)

简介: C++之模拟实现vector(下)

五、capacity

1.size

容器的元素个数

size_t size() const
    {
      return _finish - _start;
    }

2.capacity

容器的容量

size_t capacity() const
    {
      return _endOfStorage - _start;
    }

3.empty

判空函数

bool empty()
    {
      return _start == _finish;
    }

4.resize

改变元素个数

void resize(size_t n, const T& value = T())
    {
      if (n > size())
      {
        if (n > capacity())
        {
          reserve(n);
        }
        while (_finish != _start + n)
        {
          *_finish = value;
          _finish++;
        }
      }
      _finish = _start + n;
    }

5.reserve

改变容量

void reserve(size_t n)
    {
      if (n > capacity())
      {
        size_t oldsize = size();
        T* temp = new T[n];
        if (_start)
        {
          //memcpy(temp, _start, sizeof(T)* len);
          //这里不能使用memcpy,因为它进行的是浅拷贝,会导致原空间与新空间的内容指向同一空间,当原空间被销毁时,析构函数会将它所指的空间也销毁,导致新空间指向为野指针,导致程序崩溃
          for (size_t i = 0; i < oldsize; ++i)//只能一个元素一个元素的赋值(赋值运算符重载进行深拷贝)
          {
            temp[i] = _start[i];
          }
          delete[] _start;
        }
        _start = temp;
        _finish = _start + oldsize;
        _endOfStorage = _start + n;
      }
    }

六、access

1.普通对象的接口(可读可写)

T& operator[](size_t pos)
    {
      assert(pos < size());
      return _start[pos];
    }

2.const对象的接口(只读)

const T& operator[](size_t pos)const
    {
      assert(pos < size());
      return _start[pos];
    }

七、私有属性

private:
    iterator _start; // 指向数据块的开始
    iterator _finish; // 指向有效数据的尾
    iterator _endOfStorage; // 指向存储容量的尾

八、测试

主函数:

//test.cpp
#include"vector.h"
int main()
{
  //Jinger::Test1();
  //Jinger::Test2();
  //Jinger::Test3();
  //Jinger::Test4();
  Jinger::Test5();
  return 0;

测试:

void Test1()
  {
    vector<int> v;
    v.resize(10, -1);
    for (auto e : v)
    {
      cout << e << " ";
    }
    cout << endl;
  }

运行结果:

void Test2()
  {
    vector<int> v;
    v.push_back(1);
    v.push_back(2);
    v.push_back(3);
    v.push_back(4);
    v.push_back(4);
    v.push_back(4);
    vector<int>::iterator it = find(v.begin(), v.end(), 3);
    if (it != v.end())
    {
      it = v.insert(it, 30);
    }
    // insert以后 it还能否继续使用 -- 不能,可能发生扩容导致迭代器失效(野指针)
    //如果要继续使用it就需要对it进行更新,insert函数的返回值就是更新后的it值。
    (*it)++;
    *it *= 100;
    for (auto e : v)
    {
      cout << e << " ";
    }
    cout << endl;
  }

void Test3()
  {
    vector<int> v;
    v.push_back(1);
    v.push_back(2);
    v.push_back(3);
    v.push_back(4);
    // it失效还是不失效? ——失效,因为it位置的内容被删除,所有it的含义被改变了(此时,it会指向被删除元素的下一个元素)
    vector<int>::iterator it = find(v.begin(), v.end(), 4);
    if (it != v.end())
    {
      v.erase(it);
    }
    // 读 
    cout << *it << endl;
    // 写
    (*it)++;
    cout << *it << endl;
    for (auto e : v)
    {
      cout << e << " ";
    }
    cout << endl;
  }

//erase操作会导致it迭代器失效。再次使用时要进行更新它(erase函数的返回值就是更新后的it迭代器,此时它指向刚刚被删除元素的下一个元素)
  //虽然部分编译器(linux的g++下不报错)中erase后的迭代器还能继续使用,但不能保证所有编译器下它都不报错,因此我们同意认为erase后的迭代器会失效,如果再次使用它必须要更新它
  void Test4()
  {
    // 要求删除所有偶数
    vector<int> v;
    v.push_back(1);
    v.push_back(2);
    v.push_back(2);
    v.push_back(3);
    v.push_back(4);
    v.push_back(4);
    v.push_back(4);
    vector<int>::iterator it = v.begin();
    while (it != v.end())
    {
      if (*it % 2 == 0)
      {
        it = v.erase(it);
      }
      else
      {
        it++;
      }
    }
    for (auto e : v)
    {
      cout << e << " ";
    }
    cout << endl;
  }

void Test5()
  {
    vector<vector<int>> vv;
    vector<int> v(5, 1);
    vv.push_back(v);
    vv.push_back(v);
    vv.push_back(v);
    vv.push_back(v);
    vv.push_back(v);
    for (size_t i = 0; i < vv.size(); ++i)
    {
      for (size_t j = 0; j < vv[i].size(); ++j)
      {
        cout << vv[i][j] << " ";
      }
      cout << endl;
    }
    cout << endl;
  }


总结

以上就是今天要讲的内容,本文介绍了作者自己实现的vector类的相关类成员函数,如果文章中的内容有错误或者不严谨的部分,欢迎大家在评论区指出,也欢迎大家在评论区提问、交流。

最后,如果本篇文章对你有所启发的话,希望可以多多支持作者,谢谢大家!

目录
打赏
0
0
0
0
0
分享
相关文章
【C++】vector介绍+模拟实现
【C++】vector介绍+模拟实现
【c++丨STL】vector的使用
本文介绍了C++ STL中的`vector`容器,包括其基本概念、主要接口及其使用方法。`vector`是一种动态数组,能够根据需要自动调整大小,提供了丰富的操作接口,如增删查改等。文章详细解释了`vector`的构造函数、赋值运算符、容量接口、迭代器接口、元素访问接口以及一些常用的增删操作函数。最后,还展示了如何使用`vector`创建字符串数组,体现了`vector`在实际编程中的灵活性和实用性。
90 4
C++ 中 std::array<int, array_size> 与 std::vector<int> 的深入对比
本文深入对比了 C++ 标准库中的 `std::array` 和 `std::vector`,从内存管理、性能、功能特性、使用场景等方面详细分析了两者的差异。`std::array` 适合固定大小的数据和高性能需求,而 `std::vector` 则提供了动态调整大小的灵活性,适用于数据量不确定或需要频繁操作的场景。选择合适的容器可以提高代码的效率和可靠性。
65 0
【c++丨STL】vector模拟实现
本文深入探讨了 `vector` 的底层实现原理,并尝试模拟实现其结构及常用接口。首先介绍了 `vector` 的底层是动态顺序表,使用三个迭代器(指针)来维护数组,分别为 `start`、`finish` 和 `end_of_storage`。接着详细讲解了如何实现 `vector` 的各种构造函数、析构函数、容量接口、迭代器接口、插入和删除操作等。最后提供了完整的模拟实现代码,帮助读者更好地理解和掌握 `vector` 的实现细节。
42 0
|
3月前
|
【C++打怪之路Lv9】-- vector
【C++打怪之路Lv9】-- vector
32 1
【C++篇】从零实现 C++ Vector:深度剖析 STL 的核心机制与优化2
【C++篇】从零实现 C++ Vector:深度剖析 STL 的核心机制与优化
85 6
【C++篇】从零实现 C++ Vector:深度剖析 STL 的核心机制与优化1
【C++篇】从零实现 C++ Vector:深度剖析 STL 的核心机制与优化
107 7
【C++篇】解密 STL 动态之魂:全面掌握 C++ vector 的高效与优雅
【C++篇】解密 STL 动态之魂:全面掌握 C++ vector 的高效与优雅
68 3
|
3月前
|
C++
【C++】C++ STL探索:Vector使用与背后底层逻辑(三)
【C++】C++ STL探索:Vector使用与背后底层逻辑
AI助理

你好,我是AI助理

可以解答问题、推荐解决方案等