【发布时间】:2011-03-31 11:13:28
【问题描述】:
我这里有一个奇怪的。当我传入以下字符串时,strtol、atol 和 atoi 都返回不正确的值:
long test = strtol("3087663490", &p, 10);
根据我的调试器,它返回 2147483647。我对此完全感到困惑。有什么建议吗?
【问题讨论】:
标签: c visual-studio-2010 string
我这里有一个奇怪的。当我传入以下字符串时,strtol、atol 和 atoi 都返回不正确的值:
long test = strtol("3087663490", &p, 10);
根据我的调试器,它返回 2147483647。我对此完全感到困惑。有什么建议吗?
【问题讨论】:
标签: c visual-studio-2010 string
您的值大于带符号的long 类型可以表示的值。试试:
unsigned long test = strtoul("3087663490", &p, 10);
(你得到 2147483647,因为它是 LONG_MAX 或 0x7FFFFFFF)
【讨论】:
正确测试来自strtol() 的错误很棘手。您需要类似于以下的代码:
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <limits.h>
int main()
{
char *n = "3087663490";
char *p;
long test;
errno = 0;
test = strtol(n, &p, 10);
if (p == n)
printf("No digits found.\n");
else if ((test == LONG_MIN || test == LONG_MAX) && errno == ERANGE)
printf("Value out of range.\n");
else
printf("Value is %ld\n", test);
return 0;
}
运行它会显示您的问题是什么 - Value out of range.。使用更宽的类型,例如long long(和strtoll())。
【讨论】:
在您的系统上,long 似乎是 32 位类型。如果是这种情况,3087663490 大于 LONG_MAX。来自strtol(3) man page:
如果发生溢出,
strtol()返回LONG_MAX。
您需要在您的机器上使用无符号类型来表示该数字:
unsigned long test = strtoul("3087663490", &p, 10);
应该可以正常工作。
【讨论】:
long long 类型和strtoll()。
从 strtol 返回后检查p 的值。我相信,如果您超出大小限制,则返回值将是 LONG_MAX 并且指针仍将是数字指针,而不是空格或文本。
我在检查后还看到errno 将设置为ERANGE。
【讨论】: