0


STL容器入门基础Ⅰvector

STL是C++标准库的重要组成部分,vector容器在实际中非常的重要,它常见的接口使用我们都要熟悉,这一篇肝一波vector容器常见的接口使用,帮助大家深入理解

vector容器的接口使用

vector容器的初始化

//构造函数初始化
void test_vector1()
{
  //存储int
  vector<int>v1;
  v1.push_back(1);
  v1.push_back(2);
 
  //存储double
  vector<double>v2;
  v2.push_back(1.1);
  v2.push_back(2.2);

  //存储string
  vector<string>v3;
  v3.push_back("李白");//
  v3.push_back("杜甫");
  v3.push_back("苏轼");
  //用10个5初始化 
  vector<int>v4(10,5);
}

vector容器的遍历方法

//vector容器的遍历
void test_vector2()
{
  vector<int>v1;
  v1.push_back(1);
  v1.push_back(2);
  v1.push_back(3);
  v1.push_back(4);
  //1.下标+[]
  for (size_t i = 0; i < v1.size(); ++i)
  {
   cout << v1[i] << " ";//打印1 2 3 4
  }
  cout << endl;
  //2.迭代器
  vector<int>::iterator it = v1.begin();
  while (it != v1.end())
  {
   cout << *it <<" ";//打印1 2 3 4
   ++it;
  }
  cout << endl;
  //3.范围for
  for (auto e : v1)
  {
   cout << e << " ";//打印1 2 3 4
  }
  cout << endl;
}

vector容器的空间增长问题

//测试增容 vs下
void test_vector3()
{
  size_t sz;
  vector<int> v;
  v.reserve(100);//提前开辟空间 可以减少扩容
  sz = v.capacity();//初始容量 
  cout << "making v grow:\n";
  for (int i = 0; i < 100; ++i)
  {
   v.push_back(i);
   if (sz != v.capacity())
   {
    sz = v.capacity();
    cout << "capacity changed: " << sz << '\n';//扩容1.5倍
   }
  }
  //vector<int> v1;
  //v1.resize(100, 1);// resize扩容同时初始化
  v.resize(10);
  cout << v.size() << endl;//打印10  resize扩容 不会缩容
  cout << v.capacity()<<endl;//打印100 
}

vector容器指定位置插入删除

//指定位置插入 删除  
//使用迭代器 不支持下标
void test_vector4()
{
  vector<int>v1;
  v1.push_back(1);
  v1.push_back(2);
  v1.push_back(3);
  v1.push_back(4);
  //头插1个0
  v1.insert(v1.begin(), 0);
  for (auto e : v1)
  {
    cout << e << " ";//打印0 1 2 3 4
  }
  cout << endl;

  //第三个位置插入2
  v1.insert(v1.begin() + 3, 2);
  for (auto e : v1)
  {
    cout << e << " ";//打印0 1 2 2 3 4
  }
  cout << endl;

  //头删三次
  v1.erase(v1.begin());
  v1.erase(v1.begin());
  v1.erase(v1.begin());
  for (auto e : v1)
  {
    cout << e << " ";//打印2 3 4
  }
  cout << endl;
}

vector容器的查找

//要复用find查找函数 
void test_vector5()
{
  vector<int>v1;
  v1.push_back(1);
  v1.push_back(2);
  v1.push_back(3);
  v1.push_back(4);
  //查找3删除
  auto pos=find(v1.begin(), v1.end(), 3);
  if (pos != v1.end())
  {
   cout << "找到了" << endl;
   v1.erase(pos);//删除3
  }
  else
  {
   cout << "没有找到" << endl;
  }
  //遍历
  for (auto e : v1)
  {
   cout << e << " ";
  }
  cout << endl;
}

vector容器数据的排序

//调用sort排序
//随机访问迭代器 
void test_vector6()
{
  vector<int>v1;
  v1.push_back(1);
  v1.push_back(3);
  v1.push_back(9);
  v1.push_back(7);
  v1.push_back(10);
  sort(v1.begin(), v1.end());//默认升序 
  //sort(v1.begin(), v1.end(),greater<int>());//使用仿函数排降序
  for (auto e : v1)
  {
   cout << e << " ";//1 3 7 9 10
  }
  cout << endl;
}

vector容器的模拟实现

模拟实现vector容器可以帮助我们更好的理解底层是如何实现的

模拟实现函数的接口

template<class T>
class vector
{
public:

    typedef T* iterator;
    typedef const T* const_iterator;

    //无参的构造
    vector()
        :_start(nullptr)
        , _finish(nullptr)
        , _endofstorage(nullptr)
    {}

    //带参构造 现代写法 迭代器区间 
    template <class InputIterator>
    vector(InputIterator first, InputIterator last)
        :_start(nullptr)
        , _finish(nullptr)
        , _endofstorage(nullptr)
    {
        while (first != last)
        {
            push_back(*first);
            ++first;
        }
    }
    //交换函数
    void swap(vector<T>& v)
    {
        std::swap(_start, v._start);
        std::swap(_finish, v._finish);
        std::swap(_endofstorage, v._endofstorage);
    }
    //拷贝构造现代写法 复用带参构造
    vector(const vector<T>& v)
        :_start(nullptr)
        , _finish(nullptr)
        , _endofstorage(nullptr)
    {
        vector<T> tmp(v.begin(), v.end());
        this->swap(tmp);
        cout << "调用拷贝构造" << endl;
    }
    //赋值
    vector<T>& operator=(vector<T> v)
    {
        cout << "调用赋值" << endl;
        this->swap(v);
        return *this;
    }
    //析构
    ~vector()
    {
        if (_start)
        {
            delete[]_start;
            _start = _finish = _endofstorage = nullptr;

        }
    }

    //大小
    size_t size()const
    {
        return _finish - _start;
    }
    //容量
    size_t capacity()const
    {
        return _endofstorage - _start;
    }

    //迭代器
    iterator begin()
    {
        return _start;
    }

    const_iterator begin()const
    {
        return _start;
    }

    iterator end()
    {
        return _finish;
    }

    const_iterator end()const
    {
        return _finish;
    }

    //扩容函数
    void reserve(size_t n)
    {
        size_t sz = size();
        if (n > capacity())
        {
            T* tmp = new T[n];//先开辟新空间
            if (_start)//有空间才拷贝
            {
                //memcpy(tmp, _start, size() * sizeof(T));//拷贝数据
                for (size_t i = 0; i < size(); ++i)
                {
                    tmp[i] = _start[i];
                }
                delete[]_start;//释放旧空间
            }
            _start = tmp;//在指向新空间
        }
        //同时让finish和capacity都指向新空间
        _finish = _start + sz;
        _endofstorage = _start + n;
    }
    //扩容加初始化 注意分情况
    void resize(size_t n, const T& val = T())
    {
        if (n > capacity())
        {
            reserve(n);
        }
        if (n > size())
        {
            while (_finish < _start + n)
            {
                *_finish = val;
                ++_finish;
            }
        }
        else
        {
            _finish = _start + n;
        }
    }

    //尾部插入数据
    void push_back(const T& x)
    {
        if (_finish == _endofstorage)
        {
            size_t newcapacity = capacity() == 0 ? 4 : capacity() * 2;
            reserve(newcapacity);
        }
        *_finish = x;//插入到finish位置
        ++_finish;//更新大小
    }
    //尾删数据
    void pop_back()
    {
        if (_finish > _start)
        {
            --_finish;
        }
    }
    //返回数据
    T& operator[](size_t pos)
    {
        assert(pos < size());
        return _start[pos];
    }
    const T& operator[](size_t pos)const
    {
        assert(pos < size());
        return _start[pos];
    }

    //pos位置插入x
    iterator insert(iterator pos, const T& x)
    {
        assert(pos >= _start && pos <= _finish);
        //先扩容
        if (_finish == _endofstorage)
        {
            size_t n = pos - _start;//扩容后pos失效,要更新
            size_t newcapacity = capacity() == 0 ? 4 : capacity() * 2;
            reserve(newcapacity);
            pos = _start + n;
        }
        //挪动数据
        iterator end = _finish - 1;
        while (end >= pos)
        {
            *(end + 1) = *end;
            --end;
        }
        *pos = x;
        ++_finish;

        return pos;
    }
    //erase 
    iterator erase(iterator pos)
    {
        assert(pos >= _start && pos < _finish);
        iterator it = pos + 1;
        while (it != _finish)
        {
            *(it - 1) = *it;
            ++it;//...
        }
        --_finish;
        return pos;//指向最后被删除元素的后一个位置
    }

    void clear()
    {
        _finish = _start;
    }
private:
    iterator _start;
    iterator _finish;
    iterator _endofstorage;
};

模拟实现的测试

测试要和上面模拟接口放到一个命名空间里面

//尾插 尾删测试
void Test_vector1()
{
  vector<int>v;
  v.push_back(1);
  v.push_back(2);
  v.push_back(3);
  v.push_back(4);
  v.push_back(5);

  v.insert(v.begin(), 0);//头部插入0

  v.pop_back();//删除两个
  v.pop_back();
  vector<int>::iterator it = v.begin();
  while (it != v.end())
  {
   cout << *it << " ";//打印0 1 2 3
   ++it;
  }
  cout << endl;
  }

//指定位置插入测试
void Test_vector2()
{
  vector<int>v;
  v.push_back(1);
  v.push_back(2);
  v.push_back(3);
  v.push_back(4);
  //指定位置偶数前插入20
  vector<int>::iterator it = v.begin();
  while (it != v.end())
  {
   if (*it % 2 == 0)
   {
    //要考虑迭代器失效
    it = v.insert(it, 20);
    ++it;
   }
    ++it;
  }
  for (auto e : v)
  {
   cout << e << " ";
  }
  cout << endl;
}

//指定位置删除 
void Test_vector3()
{
  vector<int>v;
  v.push_back(1);
  v.push_back(2);
  v.push_back(3);
  v.push_back(4);
  v.push_back(5);
  v.push_back(2);
  //删除偶数
  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 << " ";//打印1 3 5
  }
  cout << endl;
}

//迭代器区间初始化
void Test_vector4()
{
  vector<int>v;
  v.push_back(1);
  v.push_back(2);
  v.push_back(3);
  v.push_back(4);
  //迭代器模板
  vector<int>v1(v.begin(), v.end());

  std::string s("hello");
  vector<char>v2(s.begin(), s.end());

  for (auto e : v1)
  {
    cout << e << " ";//打印1 2 3 4
  }
  cout << endl;

  for (auto e : v2)
  {
    cout << e << "";//打印 hello
  }
  cout << endl;

}

//拷贝构造和赋值测试
void Test_vector5()
{
  vector<int>v;
  v.push_back(1);
  v.push_back(2);
  v.push_back(3);
  v.push_back(4);
  //迭代器区间
  vector<int>v1(v.begin(), v.end());
  for (auto e : v1)
  {
   cout << e << " ";
  }
  cout << endl;

  vector<int>v3(v);//调用构造 

  for (auto e : v3)
  {
   cout << e << " ";
  }
  cout << endl;
}

学习vector一定要学会查看文档,这里放一个官方文档链接vector容器文档,vector在实际中非常的重要,我们只要熟悉常见的接口就可以

希望这篇文章大家有所收获,我们下篇见


本文转载自: https://blog.csdn.net/qq_72486849/article/details/125947593
版权归原作者 小圣编程 所有, 如有侵权,请联系我们删除。

“STL容器入门基础Ⅰvector”的评论:

还没有评论