C++异常:来自编程原理的out_of_range_error
C++ exceptions: out_of_range_error from Programming Principles
我有几个关于C++异常的问题。作为参考,我正在通过Bjarne Stroustrup的"使用C++编程原理和实践"学习C++。
我认为我的第一个问题很简单:在第147页左右,我们谈论的是处理引用向量范围之外的索引的例外情况。所以他的试跳拦截是
int main(){
try{
vector<int> v;
int x;
while(cin>>x)
v.push_back(x);
for(int i = 0; i<=v.size();i++)
cout<<"v["<<i<<"] == "<<v[i]<<endl;
} catch (out_of_range_error){
cerr<<"Oops! Range errorn"
return 1;
} catch(...){
cerr<<"Exception: something went wrongn";
return 2;
}
}
所以我的问题是什么是out_of_range_error?!在书的早期,他提到了使用头文件,这样新人就不必关心细微差别。该文件位于此处但是out_of_range_error不存在。只有您可以正常检查的标准out_of_range异常(在导入stdexcept之后)。即使我使用该文件(我通常不使用),编译器(g++)也会告诉我它需要out_of_range_error的标识符。那么,这只是这本大规模生产的书中的一些拼写错误吗?还是我错过了什么?
我的第二个问题是关于同一主题,如果我不导入他提供的文件,而是只导入:
#include <iostream>
#include <stdexcept>
#include <vector>
using namespace std;
/*
#include "std_lib_facilities.h"
*/
int main()
{
try
{
vector<int> newVec;
int x;
while(cin>>x)
newVec.push_back(x);
for(int i = 0; i<=newVec.size()+200;i++)
cout<<newVec[i]<<endl;
return 0;
}//try
catch (out_of_range)
{
cerr<<"runtime error: "<<endl;
return 1;
}//catch
}//main()
然后我的代码运行时不调用catch块,即使我最后引用了newVec[newVec.size()+200]。它只是返回一堆0和其他随机分布的整数。我预计这些只是为newVec分配的下一个内存位,Vector在这里并不特别,数组也会发生同样的情况。
那么,为什么C++不进行任何范围检查呢?或者它做范围检查而不在乎?
如果我使用
vector<int> v(10);
v.at(20) = 100;
然后我得到一个错误,但如果我只想引用或分配给v[20],我不会有问题。为什么会这样?
这在C++中常见吗?您是否经常需要额外的代码来强制C++来注意数组边界?这似乎非常危险,来自java背景。Java会立即提醒您任何索引错误,但C++似乎满足于让您继续使用不正确的逻辑。
非常感谢您的回复,很抱歉问这个问题太长时间了。
相对于你的第一个问题,我确信out_of_range_error
是一个拼写错误。应该有out_of_range
(更多信息请参阅本书第19.4节)。
至于第二个问题,那么向量的operator []
不会抛出异常std::out_of_range
,它模拟了数组的bahaviour。因此,这只是一种未定义的行为。如果你想检查范围,那么你必须使用成员函数at
顺便说一句,如果这本书在网站上有错误,那么你应该仔细阅读
激励C++及其标准库设计的最重要原则之一是"你不需要为你不需要的东西付费"。
正确编写的代码不应该越界访问数组(或向量),因此他们不需要边界检查,因此他们也不应该被迫为此付费。边界检查可以很容易地使数组访问的成本翻倍。类似的设计可以在整个C++标准库中看到,例如,std::lock_guard
与std::unique_lock
、std::condition_variable
与std::condition_variable_any
。在每种情况下,后一个类都会以额外的成本添加额外的功能,因此不需要额外功能的用户可以简单地使用更轻量级的版本。
如果确实需要边界检查,则std::vector
为此提供了成员函数at()
。
- 为什么我的向量::擦除调用会抛出"vector subscript out of range"?
- 解决方案在第 25 行执行错误'out of bounds'
- C++ 向量加减抛出"expression: vector subscript out of range."错误
- 从 MSVC14 切换到 MSVC16 会导致"compiler is out of heap space (C1060)"错误
- 庞大的初始化列表,如何修复"fatal error C1060: compiler is out of heap space"
- 如何解决'vector subscript out of range'错误?
- 在析构函数中调用"delete"运算符时"compiler is out of heap space"编译器错误
- 空集"Out of bound iterator"
- 在 std::unordered_map 中插入新的键/值对会导致"out of range"异常
- 注册 Clang 检查器时出错:"out-of-line-definition of register"
- QList::operator[]中的断言失败<T>:QJoysticks 中的"index out of range"
- 尝试获取矩阵的正确对角线会导致"vector out of range"错误
- 运算符方法和返回对象"out-of-scope"?
- 如何使用 mpi 分散修复"vector subscript out of range"?
- 如何修复邻接列表中的"Debug Assertion Failed" "vector subscript out of range"
- "Vector subscript out of range",在返回声明?
- QList<T>::operator[]: "index out of range" 中的断言失败
- 多次调用存储过程时C++连接器"Commands out of sync" mySQL
- 如何处理C++'index out of bounds error'?
- MySQL 异常"connection lost during query"、"MySQL server has gone away"和"command out of sync"