5

Intro (from Eric Lippert Blog) :

Vexing exceptions are the result of unfortunate design decisions. Vexing exceptions are thrown in a completely non-exceptional circumstance, and therefore must be caught and handled all the time.

The classic example of a vexing exception is Int32.Parse, which throws if you give it a string that cannot be parsed as an integer. But the 99% use case for this method is transforming strings input by the user, which could be any old thing, and therefore it is in no way exceptional for the parse to fail. Worse, there is no way for the caller to determine ahead of time whether their argument is bad without implementing the entire method themselves, in which case they wouldn't need to be calling it in the first place.

Now the important part:

This unfortunate design decision was so vexing that of course the frameworks team implemented TryParse shortly thereafter which does the right thing.

From MSDN Int32.TryParse:

Return Value Type: System.Boolean true if s was converted successfully; otherwise, false.

So colleague recenly was working on some small bit of code that required checking if a string is a number so after thinking about it and realizing there is no good C++ solution(basically it is a for__each/find_if or boost:lexical_cast try catch) I thought how nice it would be to have is_convertible or something from boost?

Ofc i can wrap boost lexical_cast and return true at the end of try block and return false at the end of catch block but I prefer existing practice :) solutions.

4

3 回答 3

4

> 所以同事最近正在编写一些需要检查字符串是否为数字的代码,所以在考虑并意识到没有好的 C++ 解决方案之后

在 C++11 中,你有std::stoland/or std::stod,它可以满足你的需要。

更新 如果您不想使用异常,那么strtol(str, &endp)将进行转换。

您可以str == endp在通话后检查是否;如果它们相同,则无法进行转换(因为 endp 将指向字符串未转换部分的开头)

像这样:

strtol(str, &endp);
if (endp==str) { /* no conversion occurred */ }
于 2012-11-28T17:05:42.673 回答
4

如果你可以使用 boost,那么你可以使用boost::conversion::try_lexical_convert

#include <boost/lexical_cast/try_lexical_convert.hpp>

std::string str("1.2");
double res;
if(boost::conversion::try_lexical_convert<double>(str, res)){
   //everything normal
}
else{
   //we got a problem
}
于 2017-02-23T15:02:50.763 回答
-1

不是真的,老实说,据我所知,没有try_lexical_cast,但你可以做两件事。

Own 是使用流并测试提取是否成功,而不是在大多数情况下在lexical_cast内部使用流:

 std::string str="56.7";
 std::istringstream ss(str);
 double d;
 if(ss >> d) {
     //passed
 }
 else //failed

或者当然正如你提到的,你可以包装lexical_cast

于 2012-11-28T10:33:20.680 回答