C语言有符号整数隐式转换无符号整数出现的陷阱

时间:2023-01-11 23:39:24
#include <stdio.h>
#include <string.h>
int main()
{
char *s = "rt"; //长度为2
char *t = "tyr"; //长度为3
printf("%d\n", strlen(s)-strlen(t)>0); //1
printf("%d\n", (int)(strlen(s)-strlen(t))>0); //0
return 0;
}
该程序意思是比较字符串数组s和字符串数组t的长度大小。按我们的理解,在第7行应该返回false,即输出0。
c语言执行运算时,如果它的一个运算数是无符号的,而另一个是有符号的,那么c语言会隐式的将有符号参数强制类型转换为无符号数,并假设这两个数都是非负的,来执行则会个运算。
再看这个程序,第7行输出1的原因是由于函数size_t  strlen(const char *s) 的返回类型是size_t,查看stdio.h可知size_t是无符号整形,当 s数组长度比t数组长度小1时,判断式表示比较-1u>0。首先-1会转换为无符号整形,即4294967295,显然大于0。所以 这时候比较完之后返回为true,输出为1。我们可以对 strlen(s)-strlen(t),进行强制转换为一般整形数,再与0比较,就能避免了这种意想不到的错误。