vector
💬 :如果你在阅读过程中有任何疑问或想要进一步探讨的内容,欢迎在评论区畅所欲言!我们一起学习、共同成长~!
👍 :如果你觉得这篇文章还不错,不妨顺手点个赞、加入收藏,并分享给更多的朋友噢~!
1. vector 的基本介绍
基本定义
-
vector 是表示可变大小数组的序列容器。
存储特性
-
就像数组一样,vector 也采用连续存储空间来存储元素,意味着可以采用下标对 vector 的元素进行访问,和数组一样高效。
扩容机制
-
当新元素插入时,若原数组空间不足,需要重新分配大小以增加存储空间。其做法是分配一个新数组,并将全部元素移到新数组。
空间策略
-
vector 会分配一些额外的空间以适应可能的增长,不同的库采用不同的策略来权衡空间的使用和重新分配,但重新分配都应是对数增长的间隔大小,以保证在末尾插入一个元素时是在常数时间复杂度完成的。
性能权衡
-
vector 占用了更多的存储空间,以换取管理存储空间的能力,并且能够以一种有效的方式动态增长。
容器对比
-
与 deque、list 和 forward_list 等其他动态序列容器相比,vector 在访问元素时更加高效,在末尾添加和删除元素相对高效,但对于不在末尾的删除和插入操作,效率较低。与 list 和 forward_list 相比,vector 具有统一的迭代器和引用。
2. vector 的基本操作与使用
2.1 构造函数
构造函数声明 | 接口说明 |
---|---|
vector<类型> vec;(重点) | 无参构造 |
vector<类型> vec(n, val); | 构造并初始化 n 个 val |
vector<类型> vec2(vec1);(重点) | 拷贝构造 |
vector<类型> vec(起始迭代器, 结束迭代器); | 使用迭代器进行初始化构造 |
2.1.1 vector<类型> vec;(重点)
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec; // 通过无参构造创建一个空的向量cout << "Size of vec: " << vec.size() << endl; return 0;
}
2.1.2 vector<类型> vec(n, val);
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec1(5, 10); // 创建一个包含5个元素的向量,所有元素初始化为10vector<int> vec2(3); // 创建一个包含3个元素的向量,默认初始化为0for (int i : vec1) {cout << i << " ";}cout << endl;for (int i : vec2) {cout << i << " ";}cout << endl;return 0;
}
2.1.3 vector<类型> vec2(vec1);(重点)
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec1 = { 1, 2, 3, 4, 5 };vector<int> vec2(vec1); for (int i : vec2) {cout << i << " ";}cout << endl;return 0;
}
2.1.4 vector<类型> vec(起始迭代器, 结束迭代器);
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec1 = { 1, 2, 3, 4, 5 };vector<int> vec(vec1.begin(), vec1.end());// 或者用数组// int arr[] = { 1, 3, 5, 7, 9 };// vector<int> vec(arr, arr + sizeof(arr) / sizeof(arr[0]));for (int i : vec) {cout << i << " ";}cout << endl;return 0;
}
2.2 迭代器(iterator)操作
begin() (重点) | 指向容器第一个元素的正向迭代器(const 版本返回常量迭代器) |
end() (重点) | 指向容器最后一个元素的下一个位置的正向迭代器(常作为循环终止条件) |
rbegin() | 指向容器最后一个元素的反向迭代器(用于逆序遍历) |
rend() | 指向容器第一个元素的前一个位置的反向迭代器(逆序遍历终止条件) |
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec = { 10, 20, 30, 40, 50 };cout << "正向遍历:";for (auto it = vec.begin(); it != vec.end(); ++it) {cout << *it << " ";}cout << std::endl;cout << "逆序遍历:";for (auto it = vec.rbegin(); it != vec.rend(); ++it) {cout << *it << " ";}cout << endl;return 0;
}
2.3 容量操作
size() | 获取当前 |
capacity() | 获取分配给 |
empty() | 判断 |
(1)resize(n) (重点) | 调整有效元素数量
|
(2)resize(n,val) (重点) | |
reserve(n) (重点) | 预先为
|
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec = { 1, 2, 3 };cout << "(1)" << endl;cout << "当前元素数量: " << vec.size() << endl;cout << "当前容量: " << vec.capacity() << endl;cout << "vector 是否为空? " << (vec.empty() ? "是" : "否") << endl;// resize() 扩大 vector 的大小vec.resize(5, 10); cout << "(2)" << endl;cout << "大小调整为 5,新元素为 10 后:\n";cout << "新大小: " << vec.size() << endl;cout << "新容量: " << vec.capacity() << endl;cout << "元素: ";for (int val : vec) {cout << val << " ";}cout << endl;// resize() 缩小 vector 的大小vec.resize(3); cout << "(3)" << endl;cout << "大小调整为 3 后:\n";cout << "新大小: " << vec.size() << endl;cout << "当前容量: " << vec.capacity() << endl;cout << "元素: ";for (int val : vec) {cout << val << " ";}cout << endl;vec.reserve(10); cout << "(4)" << endl;cout << "预分配容量为 10 个元素后:\n";cout << "当前大小: " << vec.size() << endl;cout << "新容量: " << vec.capacity() << endl;// 添加新元素,观察内存分配行为vec.push_back(20); // 添加一个新元素cout << "(5)" << endl;cout << "添加一个元素后:\n";cout << "当前大小: " << vec.size() << endl;cout << "当前容量: " << vec.capacity() << endl;cout << "元素: ";for (int val : vec) {cout << val << " ";}cout << endl;return 0;
}
2.4 修改操作
push_back(val) (重点) | vector 的末尾添加一个元素 val ,可能触发扩容。 |
pop_back() (重点) | 删除 vector 的最后一个元素。 |
find() |
|
insert(指定位置的迭代器,插入值) | 在指定位置插入一个元素,可能触发扩容。 |
erase(指定位置的迭代器/区间) | 删除指定位置/指定区间的元素。删除后,后面的元素会向前移动一个位置。 |
swap( 另一个 vector 对象) | 交换两个 vector 的内容。 |
operator[索引] (重点) | 像数组一样通过索引访问和修改元素,不检查越界。 |
2.4.1 push_back()
+ pop_back()
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec = { 1, 2, 3 };vec.push_back(4); vec.push_back(5); cout << "尾插后元素:";for (int val : vec) {cout << val << " ";}cout << endl;vec.pop_back();cout << "尾删后元素:";for (int val : vec){cout << val << " ";}cout << endl;return 0;
}
2.4.2 find()
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;int main()
{vector<int> vec = { 1, 2, 3, 4, 5 };auto it = find(vec.begin(), vec.end(), 3);if (it != vec.end()) {cout << "找到元素: " << *it << " ,位置: " << distance(vec.begin(), it) << endl;}else {cout << "未找到元素" << endl;}return 0;
}
2.4.3 insert() + erase()
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec = { 1, 2, 4, 5 };cout << "初始元素:";for (int val : vec){cout << val << " ";}cout << endl;vec.insert(vec.begin() + 2, 3); cout << "指定位置插值后元素:";for (int val : vec) {cout << val << " ";}cout << endl;vec.erase(vec.begin() + 1);cout << "指定位置删值后元素:";for (int val : vec){cout << val << " ";}cout << endl;return 0;
}
2.4.4 swap()
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec1 = { 1, 2, 3 };vector<int> vec2 = { 4, 5, 6 };vec1.swap(vec2); cout << "vec1 after swap: ";for (int val : vec1) {cout << val << " ";}cout << endl;cout << "vec2 after swap: ";for (int val : vec2) {cout << val << " ";}cout << endl;return 0;
}
2.4.5 operator[]
#include <iostream>
#include <vector>
using namespace std;int main()
{vector<int> vec = { 10, 20, 30, 40, 50 };cout << "Element at index 2: " << vec[2] << endl; // 访问索引为 2 的元素vec[2] = 300; // 修改索引为 2 的元素cout << "Elements after modification: ";for (int val : vec) {cout << val << " ";}cout << endl;return 0;
}
3. vector 迭代器失效问题(重点)
3.1 迭代器失效简单介绍
-
迭代器的本质与作用
- 本质:底层为指针或指针封装(如
vector
迭代器即原生指针T*
)。 - 作用:使算法与底层数据结构解耦,实现通用逻辑。
- 本质:底层为指针或指针封装(如
-
迭代器失效的定义
- 核心:迭代器指向的内存空间被销毁或无效化。
- 表现:底层指针指向已释放 / 重新分配的内存。
-
失效的后果
- 直接风险:访问无效内存导致程序崩溃(未定义行为)。
- 逻辑隐患:操作失效迭代器可能引发数据破坏或运行时错误。
3.2 迭代器失效场景总结
操作类型 | 具体操作 | 失效原因 | 示例代码 | 平台差异 |
---|---|---|---|---|
引起底层空间改变 | resize | 触发内存重新分配,原指针指向的旧内存被释放 | | VS:使用失效迭代器直接崩溃 g++:可能不报错但结果异常 |
reserve | ||||
insert | 插入元素导致扩容时,原内存被释放 | | 同上 | |
push_back | ||||
assign | 覆盖原有元素可能触发扩容 | | 同上 | |
删除指定位置元素 | erase(pos) | 元素前移导致pos 及之后的迭代器失效;若删除最后元素,pos 变为end() | | VS:直接标记pos 失效g++:可能允许访问 pos-1 位置 |
特殊场景 | 删除最后元素 | erase(end()-1) 后,end() 迭代器失效 | | VS:访问end() 立即崩溃g++:可能不报错但结果异常 |
与 vector 类似的容器 | string 操作 | 插入、扩容、erase 操作后迭代器失效机制与vector 完全相同 | | VS / g++:处理方式与vector 一致 |
VS (MSVC) |
|
g++ (SGI) |
|
3.3 迭代器失效解决办法
核心逻辑:容器状态变更后,迭代器需重新指向当前有效内存,确保每次使用前均为最新有效值。
- 操作后实时更新:插入 / 删除等操作后,立即通过
begin()
/end()
重新获取迭代器,确保指向有效位置。 - 循环删除场景:利用
erase
返回值更新迭代器(it = v.erase(it)
),避免跳过元素或访问失效位置。 - 禁止缓存迭代器:避免在操作前保存迭代器,改为操作后按需实时获取。
- 防御性编程原则:假设所有容器操作均可能导致迭代器失效,使用前重新赋值迭代器(通用跨平台方案)。
4. vector 的应用
4.1 只出现一次的数字 I
只出现一次的数字
#include <iostream>
#include <vector>
using namespace std;class Solution
{
public:int singleNumber(vector<int>& nums) {int value = 0;for (auto e : nums) { value ^= e; // 异或操作:value = value ^ e}return value; }
};int main()
{Solution sol;vector<int> nums = { 4, 1, 2, 1, 2 }; cout << "只出现一次的元素:" << sol.singleNumber(nums) << endl;return 0;
}
4.2 杨辉三角
杨辉三角
#include <iostream>
#include <vector>
using namespace std;class Solution
{
public:vector<vector<int>> generate(int numRows) {vector<vector<int>> vv(numRows); // 初始化一个包含numRows行的二维向量// 填充每行的首尾元素为1,并初始化每行长度for (int i = 0; i < numRows; ++i) {vv[i].resize(i + 1, 1); // 第i行有i+1个元素,全部初始化为1}// 计算中间元素(从第3行开始,索引从2开始)for (int i = 2; i < numRows; ++i) { // i表示当前行号(从0开始,第2行对应i=2)for (int j = 1; j < i; ++j) { // j表示当前行的列号(从1开始,避开首尾的1)// 当前元素等于上一行同一列和前一列元素之和vv[i][j] = vv[i - 1][j] + vv[i - 1][j - 1];}}return vv; }
};int main()
{Solution sol;int numRows = 5; vector<vector<int>> result = sol.generate(numRows); cout << "杨辉三角前 " << numRows << " 行:" << endl;for (const auto& row : result) { // 遍历每一行for (int num : row) { // 遍历每行的元素cout << num << " ";}cout << endl; }return 0;
}
4.3 删除有序数组中的重复项
删除有序数组中的重复项
#include <iostream>
#include <vector>
using namespace std;int removeDuplicates(vector<int>& nums)
{if (nums.empty()) return 0;int k = 1;for (int i = 1; i < nums.size(); i++) {if (nums[i] != nums[i - 1]) {nums[k] = nums[i];k++;}}return k;
}int main()
{vector<int> nums = { 0,0,1,1,1,2,2,3,3,4 };cout << "Original array: ";for (int num : nums) {cout << num << " ";}cout << endl;int k = removeDuplicates(nums);cout << "New length: " << k << endl;cout << "Modified array: ";for (int i = 0; i < k; i++) {cout << nums[i] << " ";}cout << endl;return 0;
}
4.4 只出现一次的数字 II
只出现一次的数字 II
#include <iostream>
#include <vector>
using namespace std;int singleNumber(vector<int>& nums)
{int ones = 0, twos = 0;for (int num : nums) {ones = (ones ^ num) & ~twos;twos = (twos ^ num) & ~ones;}return ones;
}int main()
{vector<int> nums = { 0, 1, 0, 1, 0, 1, 99 };cout << "Input array: ";for (int num : nums) {cout << num << " ";}cout << endl;int result = singleNumber(nums);cout << "The single number is: " << result << endl;return 0;
}
4.5 只出现一次的数字 III
只出现一次的数字 III
#include <iostream>
#include <vector>
using namespace std;vector<int> singleNumber(vector<int>& nums)
{long long xor_all = 0;for (int num : nums) {xor_all ^= num;}long long diff_bit = xor_all & -xor_all;int a = 0, b = 0;for (int num : nums) {if (num & diff_bit) {a ^= num;}else {b ^= num;}}return { a, b };
}int main()
{vector<int> nums = { 1, 2, 1, 3, 2, 5 };cout << "Input array: ";for (int num : nums) {cout << num << " ";}cout << endl;vector<int> result = singleNumber(nums);cout << "The two single numbers are: " << result[0] << " and " << result[1] << endl;return 0;
}
4.6 数组中出现次数超过一半的数字
数组中出现次数超过一半的数字
#include <iostream>
#include <vector>
using namespace std;int MoreThanHalfNum_Solution(vector<int> numbers)
{int candidate = numbers[0];int count = 1;for (int i = 1; i < numbers.size(); i++) {if (numbers[i] == candidate) {count++;}else {count--;if (count == 0) {candidate = numbers[i];count = 1;}}}return candidate;
}int main()
{vector<int> numbers = { 1, 2, 3, 2, 2, 2, 5, 4, 2 };cout << "Input array: ";for (int num : numbers) {cout << num << " ";}cout << endl;int result = MoreThanHalfNum_Solution(numbers);cout << "The majority element is: " << result << endl;return 0;
}
4.7 电话号码的字母组合
电话号码的字母组合
#include <iostream>
#include <vector>
#include <string>
#include <unordered_map>
using namespace std;class Solution
{
public:vector<string> letterCombinations(string digits) {if (digits.empty()) return {};unordered_map<char, string> phoneMap{{'2', "abc"},{'3', "def"},{'4', "ghi"},{'5', "jkl"},{'6', "mno"},{'7', "pqrs"},{'8', "tuv"},{'9', "wxyz"}};vector<string> result;string current;backtrack(digits, 0, phoneMap, current, result);return result;}private:void backtrack(const string& digits, int index,const unordered_map<char, string>& phoneMap,string& current, vector<string>& result) {if (index == digits.size()) {result.push_back(current);return;}char digit = digits[index];string letters = phoneMap.at(digit);for (char c : letters) {current.push_back(c);backtrack(digits, index + 1, phoneMap, current, result);current.pop_back();}}
};int main()
{Solution sol;string digits = "23";cout << "Input digits: " << digits << endl;cout << "Letter combinations: [";vector<string> combinations = sol.letterCombinations(digits);for (int i = 0; i < combinations.size(); i++) {cout << "\"" << combinations[i] << "\"";if (i != combinations.size() - 1) {cout << ", ";}}cout << "]" << endl;return 0;
}
5. vector 的深度剖析及模拟实现
5.1 底层结构剖析
5.1.1 数据结构本质
- 动态数组实现:基于原生指针
T* _data
管理连续内存空间。 - 三要素成员变量:
size_t _size; // 当前有效元素个数 size_t _capacity; // 总分配内存容量(元素个数) T* _data; // 指向内存首地址的指针
- 内存布局特点:
- 物理空间连续,支持随机访问(符合数组特性)。
- 逻辑空间(
_size
)≤ 物理空间(_capacity
)。
5.1.2 空间管理
5.1.2.1 扩容机制核心逻辑
当 _size == _capacity
时触发扩容。流程如下:
-
计算新容量(通常为原容量的2倍)
-
分配新内存
-
迁移原有数据至新内存
-
释放旧内存
-
更新指针与容量信息
5.1.2.2 扩容函数实现
void reserve(size_t new_cap)
{if (new_cap <= _capacity) return; // 无需扩容T* new_data = new T[new_cap]; // 分配新内存std::move(_data, _data + _size, new_data); // 移动元素(C++11后优先用move)delete[] _data; // 释放旧内存_data = new_data;_capacity = new_cap;
}
5.1.2.3 扩容代价
- 时间:O (n) 元素拷贝(原始数据量较大时性能开销显著)。
- 空间:预分配策略导致内存利用率可能低于 100%。
5.2 模拟实现中的拷贝问题
使用 memcpy 拷贝的隐患
memcpy
是 C/C++ 标准库中用于内存复制的函数,将一段内存空间中内容原封不动地拷贝到另外一段内存空间中。
memcpy
的拷贝是浅拷贝。
用生活里的例子来理解浅拷贝:
假设你有个盒子(vector),专门装“租房合同”(自定义类型)—— 上面写着你租的房子的地址(指针指向动态内存)。
有一天盒子装不下了,你要换个更大的盒子(reserve 扩容)。这时如果直接原样复印(memcpy 二进制拷贝)旧盒子里的 “租房合同” 放到到新盒子里,新、旧盒子的 “租房合同” 指向相同的旧房子。
但旧盒子扔掉了(释放旧空间),旧房子也退租了(内存被释放)。这时新盒子里的 “租房合同” 就成了 “无效合同”(野指针)—— 再按上面的地址去 “租房子”(访问内存)就会出问题(程序崩溃),甚至可能因为没正确退租(内存没释放)导致后续麻烦(内存泄漏)。
- 总结:如果装的东西是 “租房合同” 这种需要自己管房子(资源管理)的类型,千万别直接复印 “租房合同”(memcpy 浅拷贝),得写一份新的 “租房合同”(深拷贝,复制房子本身)。
模拟实现 vector
的 reserve
接口时,若使用 memcpy
进行拷贝:
-
内置类型拷贝有效且高效
-
自定义类型拷贝可能导致:
-
浅拷贝问题(多个对象共享同一资源)
-
内存泄漏(原对象释放资源后,拷贝对象悬空)
-
双重释放(多个对象尝试释放同一资源)
-
正确实现: 使用深拷贝逐个构造元素,确保每个对象独立管理资源。
5.3
5.3.1 模拟实现步骤
5.3.1.1 类模板定义
template <typename T>
class vector {
private:T* _data;size_t _size;size_t _capacity;public:// 构造/析构/赋值vector();~vector();vector(const vector&);vector& operator=(const vector&);vector(vector&&) noexcept;vector& operator=(vector&&) noexcept;// 迭代器T* begin();T* end();// 容量操作size_t size() const;size_t capacity() const;void reserve(size_t);void resize(size_t);void resize(size_t, const T&);// 元素操作void push_back(const T&);void pop_back();T& operator[](size_t);
};
5.3.1.2 push_back 实现(含扩容逻辑)
void push_back(const T& val) {if (_size == _capacity) { // 触发扩容size_t new_cap = _capacity == 0 ? 1 : _capacity * 2;reserve(new_cap);}_data[_size++] = val;
}
5.3.1.3 insert 实现(处理迭代器失效)
iterator insert(iterator pos, const T& val) {size_t idx = pos - begin(); // 计算插入位置索引if (_size == _capacity) {size_t new_cap = _capacity == 0 ? 1 : _capacity * 2;reserve(new_cap);pos = begin() + idx; // 扩容后迭代器需重新定位}// 元素后移std::move_backward(pos, end(), end() + 1);_data[idx] = val;_size++;return pos; // 返回新插入位置的迭代器
}
5.3.1.4 拷贝构造实现(深拷贝)
vector(const vector& rhs) {_data = new T[rhs._capacity];_capacity = rhs._capacity;_size = rhs._size;std::copy(rhs._data, rhs._data + _size, _data);
}
5.3.1.5 拷贝赋值运算符实现(三步复制-交换法则)
vector& operator=(const vector& rhs) {if (this != &rhs) {T* new_data = new T[rhs._capacity];std::copy(rhs._data, rhs._data + rhs._size, new_data);delete[] _data;_data = new_data;_size = rhs._size;_capacity = rhs._capacity;}return *this;
}
5.3.2 完整模拟实现
#include <cstddef> // 为了使用 size_t
#include <algorithm> // 为了使用 std::move_backward 和 std::copytemplate <typename T>
class vector {
private:T* _data; size_t _size; size_t _capacity; public:vector() : _data(nullptr), _size(0), _capacity(0) {}~vector() {delete[] _data;}vector(const vector& rhs) {_data = new T[rhs._capacity];_capacity = rhs._capacity;_size = rhs._size;std::copy(rhs._data, rhs._data + rhs._size, _data); // 复制元素}// 拷贝赋值运算符vector& operator=(const vector& rhs) {if (this != &rhs) { T* new_data = new T[rhs._capacity];std::copy(rhs._data, rhs._data + rhs._size, new_data); // 复制数据delete[] _data; _data = new_data;_size = rhs._size;_capacity = rhs._capacity;}return *this;}// 迭代器T* begin() { return _data; } // 返回起始迭代器T* end() { return _data + _size; } // 返回结束迭代器// 容量操作size_t size() const { return _size; } // 返回当前元素数量size_t capacity() const { return _capacity; } // 返回总容量// 预分配内存(仅分配内存,不改变大小)void reserve(size_t new_cap) {if (new_cap <= _capacity) return; // 如果新容量不大于当前容量,则无需操作T* new_data = new T[new_cap];std::move(_data, _data + _size, new_data); // 移动元素到新内存delete[] _data; // 释放旧内存_data = new_data;_capacity = new_cap;}// 调整向量大小(调整有效元素数量)void resize(size_t new_size) {if (new_size > _capacity) {reserve(new_size); // 确保足够容量}if (new_size > _size) {// 构造新元素(默认构造)for (size_t i = _size; i < new_size; ++i) {new (_data + i) T(); // 使用 placement new 构造元素}} else {// 销毁多余元素for (size_t i = new_size; i < _size; ++i) {_data[i].~T(); // 显式调用析构函数}}_size = new_size;}// 带值初始化调整大小void resize(size_t new_size, const T& value) {if (new_size > _capacity) {reserve(new_size);}if (new_size > _size) {// 用给定值构造新元素for (size_t i = _size; i < new_size; ++i) {new (_data + i) T(value); // 带值的 placement new}} else {// 销毁多余元素for (size_t i = new_size; i < _size; ++i) {_data[i].~T();}}_size = new_size;}// 元素操作void push_back(const T& val) {if (_size == _capacity) { // 如果当前容量已满size_t new_cap = _capacity == 0 ? 1 : _capacity * 2; // 计算新容量reserve(new_cap); // 触发扩容}// 使用 placement new 构造元素new (_data + _size) T(val);++_size; // 更新大小}void pop_back() {if (_size > 0) { // 如果有元素--_size; // 减少大小_data[_size].~T(); // 显式销毁最后一个元素}}T& operator[](size_t index) {return _data[index]; // 返回指定索引的元素引用}// 在位置 pos 插入元素typename vector<T>::iterator insert(iterator pos, const T& val) {size_t idx = pos - begin(); // 计算插入位置的索引if (_size == _capacity) { // 如果需要扩容size_t new_cap = _capacity == 0 ? 1 : _capacity * 2;reserve(new_cap); // 执行扩容pos = begin() + idx; // 重新定位迭代器}// 向右移动元素,腾出空间std::move_backward(pos, end(), end() + 1);// 在位置 idx 构造新元素new (_data + idx) T(val);++_size; // 更新大小return pos; // 返回新元素的位置}
};