C++ 如何将命令行参数转换为 int?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2797813/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to convert a command-line argument to int?
提问by nosedive25
I need to get an argument and convert it to an int. Here is my code so far:
我需要获取一个参数并将其转换为 int。到目前为止,这是我的代码:
#include <iostream>
using namespace std;
int main(int argc,int argvx[]) {
int i=1;
int answer = 23;
int temp;
// decode arguments
if(argc < 2) {
printf("You must provide at least one argument\n");
exit(0);
}
// Convert it to an int here
}
回答by Thomas
Since this answer was somehow accepted and thus will appear at the top, although it's not the best, I've improved it based on the other answers and the comments.
由于这个答案以某种方式被接受,因此会出现在顶部,虽然它不是最好的,但我已经根据其他答案和评论对其进行了改进。
The C way; simplest, but will treat any invalid number as 0:
C方式;最简单,但会将任何无效数字视为 0:
#include <cstdlib>
int x = atoi(argv[1]);
The C way with input checking:
带有输入检查的 C 方式:
#include <cstdlib>
errno = 0;
char *endptr;
long int x = strtol(argv[1], &endptr, 10);
if (endptr == argv[1]) {
std::cerr << "Invalid number: " << argv[1] << '\n';
} else if (*endptr) {
std::cerr << "Trailing characters after number: " << argv[1] << '\n';
} else if (errno == ERANGE) {
std::cerr << "Number out of range: " << argv[1] << '\n';
}
The C++ iostreams way with input checking:
带有输入检查的 C++ iostreams 方式:
#include <sstream>
std::istringstream ss(argv[1]);
int x;
if (!(ss >> x)) {
std::cerr << "Invalid number: " << argv[1] << '\n';
} else if (!ss.eof()) {
std::cerr << "Trailing characters after number: " << argv[1] << '\n';
}
Alternative C++ way since C++11:
自 C++11 以来的替代 C++ 方式:
#include <stdexcept>
#include <string>
std::string arg = argv[1];
try {
std::size_t pos;
int x = std::stoi(arg, &pos);
if (pos < arg.size()) {
std::cerr << "Trailing characters after number: " << arg << '\n';
}
} catch (std::invalid_argument const &ex) {
std::cerr << "Invalid number: " << arg << '\n';
} catch (std::out_of_range const &ex) {
std::cerr << "Number out of range: " << arg << '\n';
}
All four variants assume that argc >= 2
. All accept leading whitespace; check isspace(argv[1][0])
if you don't want that. All except atoi
reject trailing whitespace.
所有四个变体都假设argc >= 2
. 都接受前导空格;检查isspace(argv[1][0])
你是否不想要那个。除了atoi
拒绝尾随空格之外的所有内容。
回答by CB Bailey
Note that your main
arguments are not correct. The standard form should be:
请注意,您的main
论点不正确。标准格式应该是:
int main(int argc, char *argv[])
or equivalently:
或等效地:
int main(int argc, char **argv)
There are many ways to achieve the conversion. This is one approach:
有很多方法可以实现转换。这是一种方法:
#include <sstream>
int main(int argc, char *argv[])
{
if (argc >= 2)
{
std::istringstream iss( argv[1] );
int val;
if (iss >> val)
{
// Conversion successful
}
}
return 0;
}
回答by HelloWorld
std::stoi from string could also be used.
也可以使用字符串中的 std::stoi。
#include <string>
using namespace std;
int main (int argc, char** argv)
{
if (argc >= 2)
{
int val = stoi(argv[1]);
// ...
}
return 0;
}
回答by Jerry Coffin
As WhirlWind has pointed out, the recommendations to use atoi
aren't really very good. atoi
has no way to indicate an error, so you get the same return from atoi("0");
as you do from atoi("abc");
. The first is clearly meaningful, but the second is a clear error.
正如 WhirlWind 所指出的,使用建议atoi
并不是很好。atoi
无法指示错误,因此您从 中获得与atoi("0");
从atoi("abc");
. 第一个显然是有意义的,但第二个是一个明显的错误。
He also recommended strtol
, which is perfectly fine, if a little bit clumsy. Another possibility would be to use sscanf
, something like:
他还推荐了strtol
,这很好,如果有点笨拙。另一种可能性是使用sscanf
,例如:
if (1==sscanf(argv[1], "%d", &temp))
// successful conversion
else
// couldn't convert input
note that strtol
does give slightly more detailed results though -- in particular, if you got an argument like 123abc
, the sscanf
call would simply say it had converted a number (123), whereas strtol
would not only tel you it had converted the number, but also a pointer to the a
(i.e., the beginning of the part it could notconvert to a number).
请注意,这strtol
确实提供了更详细的结果——特别是,如果你有一个像 一样的参数123abc
,sscanf
调用只会说它已经转换了一个数字 (123),而strtol
不仅会告诉你它已经转换了数字,而且还会告诉你指向的指针a
(即它无法转换为数字的部分的开头)。
Since you're using C++, you could also consider using boost::lexical_cast
. This is almost as simple to use as atoi
, but also provides (roughly) the same level of detail in reporting errors as strtol
. The biggest expense is that it can throw exceptions, so to use it your code has to be exception-safe. If you're writing C++, you should do that anyway, but it kind of forces the issue.
由于您使用的是 C++,因此您也可以考虑使用boost::lexical_cast
. 这几乎与 使用一样简单atoi
,但在报告错误方面也提供(大致)与 相同级别的详细信息strtol
。最大的开销是它可以抛出异常,所以要使用它,你的代码必须是异常安全的。如果您正在编写 C++,无论如何您都应该这样做,但这有点强迫问题。
回答by gentooise
The approach with istringstream can be improved in order to check that no other characters have been inserted after the expected argument:
可以改进使用 istringstream 的方法,以检查在预期参数之后是否没有插入其他字符:
#include <sstream>
int main(int argc, char *argv[])
{
if (argc >= 2)
{
std::istringstream iss( argv[1] );
int val;
if ((iss >> val) && iss.eof()) // Check eofbit
{
// Conversion successful
}
}
return 0;
}
回答by WhirlWind
Take a look at strtol(), if you're using the C standard library.
如果您使用的是 C 标准库,请查看 strtol()。
回答by Ramanand Yadav
Like that we can do....
这样我们就可以......
int main(int argc, char *argv[]) {
int a, b, c;
*// Converting string type to integer type
// using function "atoi( argument)"*
a = atoi(argv[1]);
b = atoi(argv[2]);
c = atoi(argv[3]);
}