This question already has an answer here:
这个问题已经有了答案:
- How to parse a string to an int in C++? 17 answers
- 如何在c++中解析字符串到int ?17个答案
Just have a quick question. I've looked around the internet quite a bit and I've found a few solutions but none of them have worked yet. Looking at converting a string to an int and I don't mean ASCII codes.
有个简单的问题。我已经浏览了很多互联网,找到了一些解决方案,但都没有成功。看看将字符串转换为int类型,而不是ASCII码。
For a quick run-down, we are passed in an equation as a string. We are to break it down, format it correctly and solve the linear equations. Now, in saying that, I'm not able to convert a string to an int.
对于快速运行,我们以字符串形式传入一个等式。我们要把它分解,正确的格式并解线性方程。现在,我不能把字符串转换成整数。
I know that the string will be in either the format (-5) or (25) etc. so it's definitely an int. But how do we extract that from a string?
我知道字符串要么是格式(-5),要么是(25)等等,所以它肯定是int。但是我们如何从字符串中提取它呢?
One way I was thinking is running a for/while loop through the string, check for a digit, extract all the digits after that and then look to see if there was a leading '-', if there is, multiply the int by -1.
我思考的一种方法是,运行一个for/while循环通过字符串,检查一个数字,然后提取所有的数字,然后看看是否有一个“-”,如果有,将int数乘以-1。
It seems a bit over complicated for such a small problem though. Any ideas?
不过,对于这样一个小问题,似乎有点过于复杂了。什么好主意吗?
11 个解决方案
#1
468
In C++11 there are some nice new convert functions from std::string
to a number type.
在c++ 11中,有一些来自std::字符串到数字类型的新转换函数。
So instead of
而不是
atoi( str.c_str() )
you can use
您可以使用
std::stoi( str )
where str
is your number as std::string
.
其中str为std::string。
There are version for all flavours of numbers: long stol(string)
, float stof(string)
, double stod(string)
,... see http://en.cppreference.com/w/cpp/string/basic_string/stol
有各种各样的数字的版本:长距短距(string), float stof(string), double stod(string),…参见http://en.cppreference.com/w/cpp/string/basic_string/stol
#2
52
std::istringstream ss(thestring);
ss >> thevalue;
To be fully correct you'll want to check the error flags.
要完全正确,您需要检查错误标志。
#3
28
use the atoi function to convert the string to an integer:
使用atoi函数将字符串转换为整数:
string a = "25";
int b = atoi(a.c_str());
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
#4
12
The possible options are described below:
可能的选择如下:
1. First option: sscanf()
1。第一个选项:sscanf()
#include <cstdio>
#include <string>
int i;
float f;
double d;
std::string str;
// string -> integer
if(sscanf(str.c_str(), "%d", &i) != 1)
// error management
// string -> float
if(sscanf(str.c_str(), "%f", &f) != 1)
// error management
// string -> double
if(sscanf(str.c_str(), "%lf", &d) != 1)
// error management
This is an error (also shown by cppcheck) because "scanf without field width limits can crash with huge input data on some versions of libc" (see here, and here).
这是一个错误(cppcheck也显示),因为“没有字段宽度限制的scanf可以在libc的某些版本上崩溃”(参见这里和这里)。
2. Second option: std::sto*()
2。第二个选择:std::停*()
#include <iostream>
#include <string>
int i;
float f;
double d;
std::string str;
try {
// string -> integer
int i = std::stoi(s);
// string -> float
float f = std::stof(s);
// string -> double
double d = std::stod(s);
} catch (...) {
// error management
}
This solution is short and elegant, but it is available only on on C++11 compliants compilers.
这个解决方案简短而优雅,但它只在c++ 11编译器上可用。
3. Third option: sstreams
3所示。第三种选择:sstreams
#include <string>
#include <sstream>
int i;
float f;
double d;
std::string str;
// string -> integer
std::istringstream ( str ) >> i;
// string -> float
std::istringstream ( str ) >> f;
// string -> double
std::istringstream ( str ) >> d;
// error management ??
However, with this solution is hard to distinguish between bad input (see here).
但是,使用这个解决方案很难区分错误的输入(参见这里)。
4. Fourth option: Boost's lexical_cast
4所示。第四个选项:提高lexical_cast
#include <boost/lexical_cast.hpp>
#include <string>
std::string str;
try {
int i = boost::lexical_cast<int>( str.c_str());
float f = boost::lexical_cast<int>( str.c_str());
double d = boost::lexical_cast<int>( str.c_str());
} catch( boost::bad_lexical_cast const& ) {
// Error management
}
However, this is just a wrapper of sstream, and the documentation suggests to use sstrem for better error management (see here).
然而,这只是sstream的包装器,文档建议使用sstrem来更好的错误管理(参见这里)。
5. Fifth option: strto*()
5。第五个选项:strto *()
This solution is very long, due to error management, and it is described here. Since no function returns a plain int, a conversion is needed in case of integer (see here for how this conversion can be achieved).
这个解决方案很长,因为错误管理,这里描述了它。由于没有函数返回纯整数,因此需要在整数情况下进行转换(请参阅这里以了解如何实现此转换)。
6. Sixth option: Qt
6。第六个选择:Qt
#include <QString>
#include <string>
bool ok;
std::string;
int i = QString::fromStdString(str).toInt(&ok);
if (!ok)
// Error management
float f = QString::fromStdString(str).toFloat(&ok);
if (!ok)
// Error management
double d = QString::fromStdString(str).toDouble(&ok);
if (!ok)
// Error management
Conclusions
结论
Summing up, the best solution is C++11 std::stoi() or, as a second option, the use of Qt libraries. All other solutions are discouraged or buggy.
总结一下,最好的解决方案是c++ 11 std::stoi(),或者作为第二个选项,使用Qt库。所有其他的解决方案都是不鼓励或有问题的。
#5
7
What about Boost.Lexical_cast?
Boost.Lexical_cast呢?
Here is their example:
这是他们的例子:
The following example treats command line arguments as a sequence of numeric data:
下面的示例将命令行参数视为一个数字数据序列:
int main(int argc, char * argv[])
{
using boost::lexical_cast;
using boost::bad_lexical_cast;
std::vector<short> args;
while(*++argv)
{
try
{
args.push_back(lexical_cast<short>(*argv));
}
catch(bad_lexical_cast &)
{
args.push_back(0);
}
}
...
}
#6
4
Admittedly, my solution wouldn't work for negative integers, but it will extract all positive integers from input text containing integers. It makes use of numeric_only
locale:
不可否认,我的解决方案不会对负整数起作用,但它会从包含整数的输入文本中提取所有正整数。它使用numeric_only地区:
int main() {
int num;
std::cin.imbue(std::locale(std::locale(), new numeric_only()));
while ( std::cin >> num)
std::cout << num << std::endl;
return 0;
}
Input text:
输入文本:
the format (-5) or (25) etc... some text.. and then.. 7987...78hjh.hhjg9878
Output integers:
输出整数:
5
25
7987
78
9878
The class numeric_only
is defined as:
类numeric_only定义为:
struct numeric_only: std::ctype<char>
{
numeric_only(): std::ctype<char>(get_table()) {}
static std::ctype_base::mask const* get_table()
{
static std::vector<std::ctype_base::mask>
rc(std::ctype<char>::table_size,std::ctype_base::space);
std::fill(&rc['0'], &rc[':'], std::ctype_base::digit);
return &rc[0];
}
};
Complete online demo : http://ideone.com/dRWSj
完整的在线演示:http://ideone.com/dRWSj。
#7
2
It's probably a bit of overkill, but boost::lexical_cast<int>( theString )
should to the job quite well.
这可能有点过分了,但是boost::lexical_cast
#8
1
atoi
is a built-in function that converts a string to an integer, assuming that the string begins with an integer representation.
atoi是一个内置函数,它将字符串转换为整数,假设字符串以整数表示开始。
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
#9
0
In Windows, you could use:
在Windows中,你可以使用:
const std::wstring hex = L"0x13";
const std::wstring dec = L"19";
int ret;
if (StrToIntEx(hex.c_str(), STIF_SUPPORT_HEX, &ret)) {
std::cout << ret << "\n";
}
if (StrToIntEx(dec.c_str(), STIF_SUPPORT_HEX, &ret)) {
std::cout << ret << "\n";
}
strtol
,stringstream
need to specify the base if you need to interpret hexdecimal.
strtol,stringstream需要指定基础,如果你需要解释hexdecimal。
#10
-2
there is another easy way : suppose you have a character like c='4'
therefore you can do one of these steps :
还有一个简单的方法:假设你有一个像c='4'这样的字符,因此你可以这样做:
1st : int q
1:int问
q=(int) c ; (q is now 52 in ascii table ) . q=q-48; remember that adding 48 to digits is their ascii code .
q = c(int);(q在ascii表中为52)。q = q-48;记住,给数字加48是他们的ascii码。
the second way :
第二种方法:
q=c-'0'; the same , character '0' means 48
q = c - ' 0 ';同样的,字符“0”表示48。
#11
-3
This normally works when I use it:
当我使用它的时候,通常是这样的:
int myint = int::Parse(mystring);
#1
468
In C++11 there are some nice new convert functions from std::string
to a number type.
在c++ 11中,有一些来自std::字符串到数字类型的新转换函数。
So instead of
而不是
atoi( str.c_str() )
you can use
您可以使用
std::stoi( str )
where str
is your number as std::string
.
其中str为std::string。
There are version for all flavours of numbers: long stol(string)
, float stof(string)
, double stod(string)
,... see http://en.cppreference.com/w/cpp/string/basic_string/stol
有各种各样的数字的版本:长距短距(string), float stof(string), double stod(string),…参见http://en.cppreference.com/w/cpp/string/basic_string/stol
#2
52
std::istringstream ss(thestring);
ss >> thevalue;
To be fully correct you'll want to check the error flags.
要完全正确,您需要检查错误标志。
#3
28
use the atoi function to convert the string to an integer:
使用atoi函数将字符串转换为整数:
string a = "25";
int b = atoi(a.c_str());
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
#4
12
The possible options are described below:
可能的选择如下:
1. First option: sscanf()
1。第一个选项:sscanf()
#include <cstdio>
#include <string>
int i;
float f;
double d;
std::string str;
// string -> integer
if(sscanf(str.c_str(), "%d", &i) != 1)
// error management
// string -> float
if(sscanf(str.c_str(), "%f", &f) != 1)
// error management
// string -> double
if(sscanf(str.c_str(), "%lf", &d) != 1)
// error management
This is an error (also shown by cppcheck) because "scanf without field width limits can crash with huge input data on some versions of libc" (see here, and here).
这是一个错误(cppcheck也显示),因为“没有字段宽度限制的scanf可以在libc的某些版本上崩溃”(参见这里和这里)。
2. Second option: std::sto*()
2。第二个选择:std::停*()
#include <iostream>
#include <string>
int i;
float f;
double d;
std::string str;
try {
// string -> integer
int i = std::stoi(s);
// string -> float
float f = std::stof(s);
// string -> double
double d = std::stod(s);
} catch (...) {
// error management
}
This solution is short and elegant, but it is available only on on C++11 compliants compilers.
这个解决方案简短而优雅,但它只在c++ 11编译器上可用。
3. Third option: sstreams
3所示。第三种选择:sstreams
#include <string>
#include <sstream>
int i;
float f;
double d;
std::string str;
// string -> integer
std::istringstream ( str ) >> i;
// string -> float
std::istringstream ( str ) >> f;
// string -> double
std::istringstream ( str ) >> d;
// error management ??
However, with this solution is hard to distinguish between bad input (see here).
但是,使用这个解决方案很难区分错误的输入(参见这里)。
4. Fourth option: Boost's lexical_cast
4所示。第四个选项:提高lexical_cast
#include <boost/lexical_cast.hpp>
#include <string>
std::string str;
try {
int i = boost::lexical_cast<int>( str.c_str());
float f = boost::lexical_cast<int>( str.c_str());
double d = boost::lexical_cast<int>( str.c_str());
} catch( boost::bad_lexical_cast const& ) {
// Error management
}
However, this is just a wrapper of sstream, and the documentation suggests to use sstrem for better error management (see here).
然而,这只是sstream的包装器,文档建议使用sstrem来更好的错误管理(参见这里)。
5. Fifth option: strto*()
5。第五个选项:strto *()
This solution is very long, due to error management, and it is described here. Since no function returns a plain int, a conversion is needed in case of integer (see here for how this conversion can be achieved).
这个解决方案很长,因为错误管理,这里描述了它。由于没有函数返回纯整数,因此需要在整数情况下进行转换(请参阅这里以了解如何实现此转换)。
6. Sixth option: Qt
6。第六个选择:Qt
#include <QString>
#include <string>
bool ok;
std::string;
int i = QString::fromStdString(str).toInt(&ok);
if (!ok)
// Error management
float f = QString::fromStdString(str).toFloat(&ok);
if (!ok)
// Error management
double d = QString::fromStdString(str).toDouble(&ok);
if (!ok)
// Error management
Conclusions
结论
Summing up, the best solution is C++11 std::stoi() or, as a second option, the use of Qt libraries. All other solutions are discouraged or buggy.
总结一下,最好的解决方案是c++ 11 std::stoi(),或者作为第二个选项,使用Qt库。所有其他的解决方案都是不鼓励或有问题的。
#5
7
What about Boost.Lexical_cast?
Boost.Lexical_cast呢?
Here is their example:
这是他们的例子:
The following example treats command line arguments as a sequence of numeric data:
下面的示例将命令行参数视为一个数字数据序列:
int main(int argc, char * argv[])
{
using boost::lexical_cast;
using boost::bad_lexical_cast;
std::vector<short> args;
while(*++argv)
{
try
{
args.push_back(lexical_cast<short>(*argv));
}
catch(bad_lexical_cast &)
{
args.push_back(0);
}
}
...
}
#6
4
Admittedly, my solution wouldn't work for negative integers, but it will extract all positive integers from input text containing integers. It makes use of numeric_only
locale:
不可否认,我的解决方案不会对负整数起作用,但它会从包含整数的输入文本中提取所有正整数。它使用numeric_only地区:
int main() {
int num;
std::cin.imbue(std::locale(std::locale(), new numeric_only()));
while ( std::cin >> num)
std::cout << num << std::endl;
return 0;
}
Input text:
输入文本:
the format (-5) or (25) etc... some text.. and then.. 7987...78hjh.hhjg9878
Output integers:
输出整数:
5
25
7987
78
9878
The class numeric_only
is defined as:
类numeric_only定义为:
struct numeric_only: std::ctype<char>
{
numeric_only(): std::ctype<char>(get_table()) {}
static std::ctype_base::mask const* get_table()
{
static std::vector<std::ctype_base::mask>
rc(std::ctype<char>::table_size,std::ctype_base::space);
std::fill(&rc['0'], &rc[':'], std::ctype_base::digit);
return &rc[0];
}
};
Complete online demo : http://ideone.com/dRWSj
完整的在线演示:http://ideone.com/dRWSj。
#7
2
It's probably a bit of overkill, but boost::lexical_cast<int>( theString )
should to the job quite well.
这可能有点过分了,但是boost::lexical_cast
#8
1
atoi
is a built-in function that converts a string to an integer, assuming that the string begins with an integer representation.
atoi是一个内置函数,它将字符串转换为整数,假设字符串以整数表示开始。
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
http://www.cplusplus.com/reference/clibrary/cstdlib/atoi/
#9
0
In Windows, you could use:
在Windows中,你可以使用:
const std::wstring hex = L"0x13";
const std::wstring dec = L"19";
int ret;
if (StrToIntEx(hex.c_str(), STIF_SUPPORT_HEX, &ret)) {
std::cout << ret << "\n";
}
if (StrToIntEx(dec.c_str(), STIF_SUPPORT_HEX, &ret)) {
std::cout << ret << "\n";
}
strtol
,stringstream
need to specify the base if you need to interpret hexdecimal.
strtol,stringstream需要指定基础,如果你需要解释hexdecimal。
#10
-2
there is another easy way : suppose you have a character like c='4'
therefore you can do one of these steps :
还有一个简单的方法:假设你有一个像c='4'这样的字符,因此你可以这样做:
1st : int q
1:int问
q=(int) c ; (q is now 52 in ascii table ) . q=q-48; remember that adding 48 to digits is their ascii code .
q = c(int);(q在ascii表中为52)。q = q-48;记住,给数字加48是他们的ascii码。
the second way :
第二种方法:
q=c-'0'; the same , character '0' means 48
q = c - ' 0 ';同样的,字符“0”表示48。
#11
-3
This normally works when I use it:
当我使用它的时候,通常是这样的:
int myint = int::Parse(mystring);