我遇到了一个非常奇怪的atoi(char *)
问题。我正试图将char
转换为它的数字表示(我知道它是一个数字(,98.04%的时间都很好,但其他1.96%的时间它会给我一个随机值。
这是我用来测试它的代码:
int increment = 0, repetitions = 10000000;
for(int i = 0; i < repetitions; i++)
{
char randomNumber = (char)rand()%10 + 48;
int firstAtoi = atoi(&randomNumber);
int secondAtoi = atoi(&randomNumber);
if(firstAtoi != secondAtoi)NSLog(@"First: %d - Second: %d", firstAtoi, secondAtoi);
if(firstAtoi > 9 || firstAtoi < 0)
{
increment++;
NSLog(@"First Atoi: %d", firstAtoi);
}
}
NSLog(@"Ratio Percentage: %.2f", 100.0f * (float)increment/(float)repetitions);
我使用XCode 4.6.1中的GNU99
C语言方言。第一个if(当第一个数字不等于第二个数字时(从不记录,所以两个atoi每次都返回相同的结果,但是每次的结果都不同。"错误的结果"似乎在-1000到10000之间。我还没见过9999以上或-999以下的。
请让我知道我做错了什么。
编辑:
我现在已经将角色设计更改为:
char numberChar = (char)rand()%10 + 48;
char randomNumber[2];
randomNumber[0] = numberChar;
randomNumber[1] = 0;
然而,我使用的是:
MAX(MIN((int)(myCharacter - '0'), 9), 0)
以获取整数值。
我真的很感激所有的答案!
atoi
需要一个字符串。你没有给它一个字符串,你只给了它一个char
。字符串被定义为以空字符结尾的一些字符。您正在调用UB。
来自文档:
如果str没有指向有效的C字符串,或者转换后的值超出了int表示的值范围,则会导致未定义的行为。
想要将字符"转换"为其积分表示形式吗?不要把事情搞得过于复杂;
int x = some_char;
char
已经是一个整数,而不是字符串。不要将单个char
视为文本。
如果我没有弄错,atoi
需要一个以null结尾的字符串(请参阅此处的文档(。
您传递的是一个基于堆栈的值,该值不必以null结尾。我非常惊讶它竟然做对了:如果它从来没有找到一个空终止符,它可能会把数百个垃圾数字读到永恒。如果你只想得到单个字符的数字(如中,字符的人类可读表示的数值(,为什么不直接做int numeric = randomNumber - 48
呢?