atol 函数

代码:

 1 long __cdecl atol(
 2   const char *nptr
 3   )
 4 {
 5   int c; /* current char */
 6   long total; /* current total */
 7   int sign; /* if '-', then negative, otherwise positive */
 8 
 9   /* skip whitespace */
10   while ( isspace((int)(unsigned char)*nptr) )
11   ++nptr;
12 
13   c = (int)(unsigned char)*nptr++; sign = c; /* save sign indication */
14   if (c == '-' || c == '+')
15   c = (int)(unsigned char)*nptr++; /* skip sign */
16 
17   total = 0;
18 
19   while (isdigit(c)) {
20   total = 10 * total + (c - '0'); /* accumulate digit */
21   c = (int)(unsigned char)*nptr++; /* get next char */
22   }
23 
24   if (sign == '-')
25   return -total;
26   else
27   return total; /* return result, negated if necessary */
28 }

为什么要用 (int)(unsigned char)?

因为在char 类型强制转换成int类型时,若char类型数是负数(最高位为1)有些编译器会将最高字节填充0xFF

 1 for(int i = 128; i < 131; i++)
 2     {
 3         int c = (char)i;
 4         int d = (unsigned char)i;
 5         printf("%d %d\n", c, d);
 6     }
 7 
 8 输出:
 9 -128 128
10 -127 129
11 -126 130
12 请按任意键继续. . .

因为isspace(),isdigit()这类函数接受一个int 参数,参数的值必须是一个可以用unsigned char 表示的值或者是EOF,以下是 man 手册的原文:

int isspace(int c);
int isdigit(int c);
...

These functions check whether c, which must have the value of anunsigned char or EOF,falls into a cetern charcter class according to the current locale.

所以需要用c = (int)(unsigned char)*nptr++,来确保从 *nptr++ 到 c 是进行零扩展而不是符号扩展,保证 c 中存放的是一个unsigned char 所能表示的值。

 

posted @ 2012-10-15 13:43  可乐爱上了雪碧  阅读(1258)  评论(0编辑  收藏  举报