' ' 评估为 false," " 评估为 true

问题描述 投票:0回答:9

受到K&R第5.5节中描述的程序的启发:

void strcpy(char *s, char *t)
{
    while(*s++ = *t++);
}

C 程序

if ('\0') { printf("\'\\0\' -> true \n"); }
else      { printf("\'\\0\' -> false\n"); }

if ("\0") { printf("\"\\0\" -> true \n"); }
else      { printf("\"\\0\" -> false\n"); }

打印

'\0' -> false
"\0" -> true

为什么

'\0'
"\0"
在 C 中的评价不同?

clang版本3.8.0

c arrays string null kernighan-and-ritchie
9个回答
122
投票

Stack Exchange 违反了此答案的许可条款,其显示此答案的许可证已被撤销。


42
投票

首先,你需要记住,在C中,

  • 零为假,非零为真。
  • 对于指针类型,
    NULL
    为假,非
    NULL
    为真。

正如其他人所说,

'\0'
与整数文字
0
相同,因此为 false(请参阅上面的第一个要点以了解原因)。

"\0"
是一个字符串文字,包含两个
\0
字符(一个是您显式添加的,另一个是隐式的,将由编译器添加)。字符串文字将存储在只读存储器中的某个位置。 当您使用
"\0"
时,它会转换为指向其第一个元素的指针
。这通常称为“数组衰减”。 (这就是像
char* str = "string";
这样的东西起作用的原因)。

因此,您正在有效地检查字符串文字的第一个字符的地址。由于字符串文字的地址始终为非

NULL
,因此 if 始终为 true(请参阅上面的第二个要点以了解原因)。


:数组的这种“衰变”并不总是发生。请参阅数组未衰减为指针的异常?


16
投票

'\0'
是一个数字:
0
,因此它被评估为 false(
0
= false,
!0
= true)。

但是

"\0"
是一个指向存储实际字符串的只读部分的指针,该指针不是
NULL
因此这是真的。


3
投票

首先看两个条件,

'\0'
是一个整数类型的常量,表示空字符C,与
0
相同。而
"\0"
是一个字符串文字,包含 2 个字节,指定的字节和隐式添加的空终止符字节。作为字符串文字,指针不能是
NULL

其次,在 C 中,对于

if
语句的条件,所有非零的值都被评估为
true
,零被评估为
false

根据这个规则,可以明确

'\0'
false
"\0"
评估为
true


3
投票

首先请注意,False 的十六进制值为

0x00
,True 为 0x00 以外的任何其他值。

"\0"
是一个字符串,末尾有一个字符和空终止符
'\0'
。所以它是一个字符指针,指向一个2字节的数组:
['\0', '\0']
。在这个数组中,第一个是字符,另一个是空终止符。

编译后(未优化),这个字符指针被临时分配到内存中指向这两个字节的第一个字节的地址。例如,该地址可能是十六进制的

0x18A6
。所以编译器(大多数)实际上将这两个值写入内存。因为字符串实际上是该字符串的第一个字节的地址,所以我们的表达式被解释为
0x18A6 != false
。所以,很明显
0x18A6 != 0x00
是正确的。

'\0'
就是十六进制的
0x00
0x00 != 0x00
是错误的。

这个答案是针对具有 16 位寻址的 8 位数据架构编写的。我希望这有帮助。


0
投票

' ' 是一个 null 字符,其值为 0。它用于终止一个字符串。所以它被认为是假的。

" "nullempty string。字符串中唯一的字符是终止字符串的空字符。所以它被认为是 true。


0
投票

' ' 是一个等于数字零的字符。 “”是一个字符串,我们通常在字符串末尾添加“”。不要在条件语句中使用 ' ' 或 " ",因为这很令人困惑。

建议使用以下方法:

if (array[0] != 0)
{

}

if (p != 0)
{

}

if (p != NULL)
{

}

0
投票

通过示例查看此内容..

#include <stdio.h> 

int main() 
{ 
printf( "string value\n" ); 

//the integer zero 
printf( "0.........%d\n" , 0 ); 

//the char zero, but chars are very small ints, so it is also an int 
//it just has some special syntax and conventions to allow it to seem 
//like a character, it's actual value is 48, this is based on the 
//ASCII standard, which you can look up on Wikipedia 
printf( "'0'.......%d\n" , '0' ); 

//because it is an integer, you can add it together, 
//'0'+'0' is the same as 48+48 , so it's value is 96 
printf( "'0'+'0'...%d\n" , '0'+'0' ); 

//the null terminator, this indicates that it is the end of the string 
//this is one of the conventions strings use, as a string is just an array 
//of characters (in C, at least), it uses this value to know where the array 
//ends, that way you don't have to lug around another variable to track 
//how long your string is. The actual integer value of '\0' is zero. 
printf( "'\\0'......%d\n" , '\0' ); 

//as stated, a string is just an array of characters, and arrays are tracked 
//by the memory location of their first index. This means that a string is 
//actually a pointer to the memory address that stores the first element of 
//the string. We should get some large number, a memory address 
printf( "\"0\".......%d\n" , "0" ); 

//a string is just an array of characters, so lets access the character 
//in position zero of the array. it should be the character zero, which 
//has an integer value of 48 
printf( "\"0\"[0]....%d\n" , "0"[0] ); 

//and the same thing for the empty string 
printf( "\"\\0\"[0]...%d\n" , "\0"[0] ); //equal to '\0' 

//we also said a string is just a pointer, so we should be able to access 
//the value it is pointing to (the first index of the array of characters) 
//by using pointers 
printf( "*\"0\"......%d\n" , *"0" ); 

return 0; 
}

0
投票

简单的是,至少 0(int)和 0.0(float 或 double)在 C 中具有 FALSE 值。

' ' 是整数 0。

" " 是一个字符数组。数组内部有多少个字符或这些字符是什么并不重要。

因此,' ' 的计算结果为 0,就像 77-77 的计算结果为 0 一样。 0 为假。

int x;
x = '\0';
printf("X has a value : %d");
输出:


x 的值为:0

代码:

if(0){printf("true");}

else{printf("false");}

输出:


© www.soinside.com 2019 - 2024. All rights reserved.