重载运算符“>>”上的 bad_lexical_cast 异常
Posted
技术标签:
【中文标题】重载运算符“>>”上的 bad_lexical_cast 异常【英文标题】:bad_lexical_cast exception on overloaded operator ">>" 【发布时间】:2014-08-17 13:48:18 【问题描述】:我为枚举重载了运算符“>>”:
#include <iostream>
#include <boost/lexical_cast.hpp>
using namespace std;
enum MyEnum
ONE = 0,
TWO,
TREE,
MAX
;
const char* MyEnumString[MAX] =
"ONE"
,"TWO"
,"THREE"
;
istream& operator>>(istream& is, MyEnum& myEnum)
string value;
is >> value;
myEnum = ONE;
for (int i=0; i < MAX; i++)
if (!value.compare(MyEnumString[i]))
myEnum = static_cast<MyEnum>(i);
return is;
return is;
int main()
cout << "Hello World" << endl;
boost::lexical_cast<MyEnum>(""); //Throws exception.
return 0;
我得到的输出:
你好世界 在抛出一个实例后调用终止 'boost::exception_detail::clone_impl
' what(): bad lexical cast: 源类型值不能被解释为目标
从 lexical_cast_39.hpp (1155) 抛出异常:
if (interpreter >> result)
该运算符适用于除空字符串之外的每个值。从运算符返回的输入流与一开始的输入流相同。
对于此类问题,可接受的方法是什么? 谢谢!
【问题讨论】:
【参考方案1】:问题是您告诉lexical_cast
将空字符串转换为MyEnum。你希望它做什么?不能返回真正的值,所以异常是正确的。
更详细的细分:lexical_cast
正在获取输入的空字符串,并从该值创建一个输入流。然后将其传递给您的operator>>
。当您执行is >> value;
时,它会在流上设置eof
标志(因为它试图读取字符串,并且没有剩余数据。
在您的函数返回后,它会完成if ( interpreter >> result )
,它主要检查流是否仍处于良好状态。由于不是(由于前面的eof
位),因此它失败并出现异常。
如果您希望将空字符串解释为特定值,则必须在返回之前从流中清除错误标志。就个人而言,我不会这样做,因为它会限制输入运算符在其他情况下的有用性。如果我需要这个功能,我很可能会在调用 lexical_cast 之前检查空字符串。
【讨论】:
感谢您的解释。我只是没有得到,就运算符的功能而言,将映射到默认 ONE 的随机字符串值与也应该映射到 ONE 的空字符串值之间有什么区别。除非我们将空字符串作为一个概念称为“无值”,否则您应该抛出异常是对的。 不同之处在于,随机的非空文本可以成功读入字符串,而空文本会导致输入操作失败。实际上,您的 operator>> 实现应该执行if (!(is >> value)) return is;
以正确处理输入错误。默认为任何值都会违反最小意外原则,因为没有其他类型具有类似的行为。以上是关于重载运算符“>>”上的 bad_lexical_cast 异常的主要内容,如果未能解决你的问题,请参考以下文章