C++ <array> at 函数
在访问 array 元素的所有方式中,at 是最安全的一种,因为它提供了边界检查。
at 是容器类的成员函数,用于返回指定位置的元素,同时进行边界检查。如果索引越界,会抛出 std::out_of_range 异常。
at 实现了安全的元素访问,让你在运行时能够捕获并处理越界错误。
单词释义: at 表示"在...位置",即获取指定位置处的元素。
基本语法与参数
at 是容器类的成员函数,因此你需要先有一个容器对象,然后通过点运算符 . 来调用它。
语法格式
reference at(size_type pos); const_reference at(size_type pos) const;
参数说明
- 参数:
pos- 类型:
size_type(无符号整数类型,通常是size_t) - 描述: 要访问的元素的位置(索引)。索引从 0 开始,最大有效索引是
size() - 1。
- 类型:
函数说明
- 返回值: 返回指定位置元素的引用。如果容器是常量容器,则返回常量引用。
- 效果: 返回指定位置的元素。如果索引超出有效范围(
pos >= size()),会抛出std::out_of_range异常。 - 与 operator[] 的区别:
at会进行边界检查,operator[]不进行边界检查(越界行为是未定义的)。
实例
让我们通过一系列从简单到复杂的例子,彻底掌握 at 的用法。
示例 1:基础用法 - 访问元素
实例
#include <iostream>
#include <array>
#include <stdexcept>
int main() {
// 1. 创建一个 array 并初始化
std::array<int, 5> numbers = {10, 20, 30, 40, 50};
std::cout << "array的大小是: " << numbers.size() << std::endl;
// 2. 使用 at 访问元素
std::cout << "第一个元素 (at(0)): " << numbers.at(0) << std::endl;
std::cout << "第二个元素 (at(1)): " << numbers.at(1) << std::endl;
std::cout << "第三个元素 (at(2)): " << numbers.at(2) << std::endl;
std::cout << "最后一个元素 (at(4)): " << numbers.at(4) << std::endl;
// 3. 使用循环访问所有元素
std::cout << "所有元素: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
return 0;
}
#include <array>
#include <stdexcept>
int main() {
// 1. 创建一个 array 并初始化
std::array<int, 5> numbers = {10, 20, 30, 40, 50};
std::cout << "array的大小是: " << numbers.size() << std::endl;
// 2. 使用 at 访问元素
std::cout << "第一个元素 (at(0)): " << numbers.at(0) << std::endl;
std::cout << "第二个元素 (at(1)): " << numbers.at(1) << std::endl;
std::cout << "第三个元素 (at(2)): " << numbers.at(2) << std::endl;
std::cout << "最后一个元素 (at(4)): " << numbers.at(4) << std::endl;
// 3. 使用循环访问所有元素
std::cout << "所有元素: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
return 0;
}
运行结果预期:
array的大小是: 5 第一个元素 (at(0)): 10 第二个元素 (at(1)): 20 第三个元素 (at(2)): 30 最后一个元素 (at(4)): 50 所有元素: 10 20 30 40 50
代码解析:
numbers.at(0)返回第一个元素10(索引从 0 开始)。numbers.at(4)返回最后一个元素50(因为size()是 5,有效索引是 0-4)。- 使用循环和
at可以安全地遍历所有元素。
示例 2:捕获越界异常
at 的主要优势在于它可以抛出异常,让我们能够处理越界错误。
实例
#include <iostream>
#include <array>
#include <stdexcept>
int main() {
std::array<int, 3> numbers = {10, 20, 30};
// 尝试访问越界位置
try {
std::cout << "尝试访问 at(10)..." << std::endl;
int value = numbers.at(10); // 这会抛出异常
std::cout << "值: " << value << std::endl;
}
catch(const std::out_of_range& e) {
std::cout << "捕获到异常: " << e.what() << std::endl;
}
// 正常访问
try {
std::cout << "访问 at(2): " << numbers.at(2) << std::endl;
}
catch(const std::out_of_range& e) {
std::cout << "捕获到异常: " << e.what() << std::endl;
}
return 0;
}
#include <array>
#include <stdexcept>
int main() {
std::array<int, 3> numbers = {10, 20, 30};
// 尝试访问越界位置
try {
std::cout << "尝试访问 at(10)..." << std::endl;
int value = numbers.at(10); // 这会抛出异常
std::cout << "值: " << value << std::endl;
}
catch(const std::out_of_range& e) {
std::cout << "捕获到异常: " << e.what() << std::endl;
}
// 正常访问
try {
std::cout << "访问 at(2): " << numbers.at(2) << std::endl;
}
catch(const std::out_of_range& e) {
std::cout << "捕获到异常: " << e.what() << std::endl;
}
return 0;
}
运行结果预期:
尝试访问 at(10)... 捕获到异常: array::at: __pos (which is 10) >= _Nm (which is 3) 访问 at(2): 30
代码解析:
- 当访问
at(10)时,由于索引超出范围,抛出了std::out_of_range异常。 catch(const std::out_of_range& e)捕获异常,e.what()返回异常的描述信息。- 正常的索引访问不会抛出异常。
示例 3:修改元素的值
at 返回的是引用,因此可以用来修改元素的值。
实例
#include <iostream>
#include <array>
int main() {
std::array<int, 3> numbers = {10, 20, 30};
std::cout << "修改前: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
// 使用 at() 获取引用并修改元素
numbers.at(0) = 100;
numbers.at(1) = 200;
numbers.at(2) = 300;
std::cout << "修改后: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
return 0;
}
#include <array>
int main() {
std::array<int, 3> numbers = {10, 20, 30};
std::cout << "修改前: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
// 使用 at() 获取引用并修改元素
numbers.at(0) = 100;
numbers.at(1) = 200;
numbers.at(2) = 300;
std::cout << "修改后: ";
for(size_t i = 0; i < numbers.size(); ++i) {
std::cout << numbers.at(i) << " ";
}
std::cout << std::endl;
return 0;
}
运行结果预期:
修改前: 10 20 30 修改后: 100 200 300
代码解析:
numbers.at(0) = 100;通过引用修改了第一个元素的值。- 这展示了
at()返回的是可修改的左值引用。

C++ 容器类 <array>