目录
头文件
#include <array>
模板定义
template<
class T, //数组元素的类型
std::size_t N //数组长度
> struct array;
array是封装的固定大小数组的容器
成员方法
构造函数
遵循聚合初始化规则,例如:
std::array<int, 3> a = {1, 2, 3};
1.如果不给初始值则默认为随机值;
std::array<int, 3> a;
//元素输出为:1 0 4254441
2.给出过多元素会报错 ,假如上面的数组我给出了4个元素:
[Error] too many initializers for 'std::array<int, 3ull>'
3.给出的元素不足时,剩余元素默认为0;
array<int,3> a={};
//元素输出为:0 0 0
array<int,3> a={1};
//元素输出为:1 0 0
析构函数
清空 array
operator=
使用另一个 array 来给当前 array 赋值,遵循对应元素赋值的方法。
int main(){
array<int,3> a={1,2,3};
array<int,4> b={};
b=a;
for(auto i:b) cout << i <<' ';
}
[Error] no match for 'operator=' (operand types are 'std::array<int, 4ull>' and 'std::array<int, 3ull>')
当两个数组大小相同时才可以赋值。
at
一个整值,代表元素在数组中的位置
根据元素位置(下标)访问元素,若位置超出范围抛出 std::out_of_range 异常。
array<int,3> a={1,2,3};
for(int i=0;i<3;i++) cout << a.at(i) <<' ';
输出:1 2 3
array<int,3> a={1,2,3};
for(int i=0;i<4;i++) cout << a.at(i) <<' ';
输出:1 2 3 terminate called after throwing an instance of 'std::out_of_range'
what(): array::at: __n (which is 3) >= _Nm (which is 3)
operator[]
一个整值,代表元素在数组中的位置
根据位置返回元素,与at不同的是:使用[]访问元素时不进行越界检查,越界时的行为是未定义的。与map中的operator[]不同,不会添加新元素到容器中,就是只能访问啦。
front
无参数
返回首元素的引用,若是空容器则行为未定义
int main(){
array<int,3> a={1,2,3};
a.front()=2;
cout << a.front() << ' ';
for(int i=0;i<3;i++) cout << a[i] <<' ';
}
输出:2 2 2 3
back
无参数
返回最后一个元素的引用,若是空容器则行为未定义
int main(){
array<int,3> a={1,2,3};
a.back()=2;
cout << a.back() << ' ';
for(int i=0;i<3;i++) cout << a[i] <<' ';
}
输出:2 1 2 2
data
无参数
返回底层数组的指针,指针范围从data() 到 data()+size()-1 都是可以的,如果是空容器也可以返回(不一定是空指针),但不能解引用。
begin/cbegin
无参数
返回指向数组首元素的迭代器,若数组为空则 begin()/cbegin() 的返回值等于 end() 的返回值。
可以根据 begin() 返回的迭代器更改数组中的值 ,而 cbegin() 则不可以(因为c是const的意思,只读哦)。如果 array 是 const 的那么我们就只能使用 c 前缀版本的 (r)begin / (r)end 函数了。
int main(){
array<int,3> a={1,2,3};
*a.begin()=2;
//*a.cbegin()=2; 编译时报错!
cout << *a.begin();
}
输出:2
end/cend
无参数
返回指向数组最后一个元素后一个位置的迭代器
这个位置是数组外面,没有元素的!所以另一种遍历数组的办法如下:
int main(){
array<int,3> a={1,2,3};
for(auto i=a.begin();i!=a.end();i++) cout << *i <<' '; // i是迭代器类型
}
输出:1 2 3
rbegin/crbegin
无参数
返回指向从数组尾部开始的第一个元素的迭代器即最后一个元素的迭代器,crbegin返回的迭代器不能修改元素。
这里的r是reverse的意思,即倒序。
rend()/crend()
无参数
返回指向第一个元素之前的位置的迭代器。
于是我们便得到了倒序遍历的方法:
int main(){
array<int,3> a={1,2,3};
for(auto i=a.rbegin();i!=a.rend();i++) cout << *i <<' ';
}
输出:3 2 1
empty
无参数
返回数组是否为空,即是否begin()==end()
若空则返回 true 否则返回 false,其实和定义大小是否为0有关
int main(){
array<int,3> a={1,2,3};
array<int,3> b;
array<int,0> c;
cout << a.empty() << ' '
<< b.empty() << ' '
<< c.empty() << endl;
}
输出:0 0 1
size
无参数
返回数组中元素个数
新的遍历方法:
int main(){
array<int,3> a={1,2,3};
for(int i=0;i<a.size();i++) cout << a[i] <<' ';
}
输出:1 2 3
max_size
无参数
返回容器能容纳的最多元素个数
因为 array 是固定大小的容器,所以返回值与 size() 的返回值相同。
int main(){
array<int,3> a={1,2,3};
for(int i=0;i<a.max_size();i++) cout << a[i] <<' ';
}
输出:1 2 3
fill
参数为一个数组元素类型的值
使用指定的元素填充整个数组
int main(){
array<int,3> a={1,2,3};
a.fill(99);
for(int i=0;i<a.size();i++) cout << a[i] <<' ';
}
输出:99 99 99
swap
参数为另一个array
与另一个array交换内容,不会导致迭代器或引用关联到另一个容器
待交换的两个容器大小必须相同
int main(){
array<int,3> a={1,2,3};
array<int,3> b={};
a.swap(b);
for(int i=0;i<a.size();i++) cout << a[i] <<' ';
cout << endl;
for(int i=0;i<b.size();i++) cout << b[i] <<' ';
}
输出:0 0 0
1 2 3
非成员函数
operator ==,!=,<,<=,>,>=,<=>
如要比较,首先 array 中的元素是可比的(比如定义了重载,或本身就是可比)
其次,数组的元素数量要相同
假若定义了array a 和 b,判断 a< b 是否成立,将从左向右按照字典序比较,若有不符合 < 关系的则返回 false,否则返回 true(此时 a 和 b 对应位置都满足 < 关系)。
关于<=>可见:<=> 语义
get<pos>
参数为数组名
返回数组对应pos位置的元素的引用,pos必须有效(在编译时就强制要求)
int main(){
array<int,3> a={1,2,3};
get<0>(a)=2;
cout << get<0>(a) << get<1>(a) << get<2>(a);
}
输出:223
swap
参数为两个容器名
只有在容器大小为0或可交换的时候才可用
int main(){
array<int,3> a={1,2,3};
array<int,3> b={4,5,6};
swap(a,b);
for(int i=0;i<a.size();i++) cout << a[i] <<' ';
cout << endl;
for(int i=0;i<b.size();i++) cout << b[i] <<' ';
// cout << a.empty() << ' '
// << b.empty() << ' '
// << c.empty() << endl;
}
输出:4 5 6
1 2 3
---------------------------------------------------------------------------------------------------------------------------------
结束!!!!
夜兰表示看到最后的你很厉害并且给自己打了个码~