C: 检查命令行参数是否为整数?

C: Checking command line argument is integer or not?

isdigit

的签名
int isdigit(int c);

atoi

的签名
int atoi(const char *nptr);

我只是想检查传递的命令行参数是整数还是not.Here是C代码:

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>

int main(int argc, char *argv[])
{
    if (argc == 1)
        return -1;

    printf ("Hai, you have executed the program : %s\n", argv[0]);
    if (isdigit(atoi(argv[1])))
        printf ("%s is a number\n", argv[1]);
    else
        printf ("%s is not a number\n", argv[1]);
    return 0;
}

但是当我传递一个有效数字时,输出并不像预期的那样:

$ ./a.out 123
Hai, you have executed the program : ./a.out
123 is not a number
$ ./a.out add
Hai, you have executed the program : ./a.out
add is not a number

我无法找出错误。

当您引用 argv[1] 时,它指的是包含值 123 的字符数组。 isdigit函数定义为单字符输入。

所以要处理这种情况,最好定义一个函数如下:

bool isNumber(char number[])
{
    int i = 0;

    //checking for negative numbers
    if (number[0] == '-')
        i = 1;
    for (; number[i] != 0; i++)
    {
        //if (number[i] > '9' || number[i] < '0')
        if (!isdigit(number[i]))
            return false;
    }
    return true;
}
if (isdigit(atoi(argv[1]))) 

将是:

if (isdigit(atoi("123")))

这将是:

if (isdigit(123))

这将是:

if ( 0 )

因为123表示ASCII字符'{'

我不知道 isdigit 到底是做什么的,但由于名称我认为它应该采用 char 参数,检查字符是否为数字,是吗?

我会这样写:(省略函数shell,只显示核心代码)

char* p = argv[1];
while (*p != '[=10=]')
{
    if (*p<'0' || *p>'9')
    {
        printf("%s is not a number", argv[1]);
        return 0;
    }
    p++;
}
printf("%s is a number", argv[1]);
return 0;

isdigit() 函数检查数字字符(“0”到“9”),这当然取决于 ASCII 值。现在从您的 atoi 返回的值不在“0”到“9”之间的 ASCII 值范围内。所以显示它不是数字。

我想我应该在已经存在的答案中添加一些内容。除了检查以 10 为基数的数字外,我认为检查并允许十六进制数字也很有用。我也允许负数。

我还添加了一些东西来检查错误输入(例如空指针、表示十进制数的字符串中的字母或表示十六进制数的字符串中的无效字母)。

注意我使用to_lower(char c)函数来确保代表十六进制的字母将小写,只是为了方便。

I return 如果字符串是有效数字则为 1(或真),否则为 0。如果它是一个有效数字,我将基数存储在参数 base 中。

// Return 1 if str is a number, 0 otherwise.
// If str is a number, store the base (10 or 16) in param base.
static int is_number(char *str, int *base)
{
    // Check for null pointer.
    if (str == NULL)
        return 0;

    int i;
    int len = strlen(str);

    // Single character case.
    if (len == 1)
    {
        *base = 10;
        return isdigit(str[0]);
    }

    // Hexadecimal? At this point, we know length is at least 2.
    if ((str[0] == '0') && (str[1] == 'x'))
    {
        // Check that every character is a digit or a,b,c,d,e, or f.
        for (i = 2; i < len; i++)
        {
            char c = str[i];
            c = to_lower(c);
            if (!(
                (c >= '0' && c <= '9') || 
                (c >= 'a' && c <= 'f')))
                return 0;
        }
        *base = 16;
    }
    // It's decimal.
    else
    {
        i = 0;
        // Accept signs.
        if (str[0] == '-' || str[0] == '+')
            i = 1;

        // Check that every character is a digit.
        for (; i < len; i++)
        {
            if (!isdigit(str[i]))
                return 0;
        }
        *base = 10;
    }
    return 1;
}

我是这样使用这个函数的:

int base, num;
if (is_number(str, &base)
    num = strtol(str, NULL, base);
// Since There is an implicit conversion from const char* to std::string
// You May use this simplified version of the check_string instead

     bool isNumeric(const string str) 
    {
        // loop Through each character in the string
        for(char x:  str)
            if(!isdigit(x)) // Check if a single character "x" its a digit
            return false;  // if its not return false 

      return true; // else return true
    }  

这是最简单的解决方案,它还会检查用户是否输入了两个以上的参数

// check for valid key
{
    for (int i = 0, n = strlen(argv[1]); i < n; i++)
    {
        if (!isdigit(argv[1][i]))
        {
            return false;
        }
    }
    return true;
}