if (!file) 和 if (file == NULL) 的区别

Posted

技术标签:

【中文标题】if (!file) 和 if (file == NULL) 的区别【英文标题】:Difference between if (!file) and if (file == NULL) 【发布时间】:2022-01-18 03:35:27 【问题描述】:

这两个版本的检查文件是否实际打开有什么区别:

FILE *file = fopen(fname, "rb");
if (!file)

    exit(1);

FILE *file = fopen(fname, "rb");
if (file == NULL)

    exit(1);

【问题讨论】:

没有区别。 唯一的区别是代码的易读性。在这方面,我认为后者更好。 根据定义,它们在计算上是相同的。唯一的区别在于风格,因此争论不休。 唯一的区别是代码的易读性。在这方面,我认为前者更好。做不必要的额外比较只会增加噪音。 无论您的个人喜好如何,您都需要识别两者。你会遇到任何一种风格,你需要知道它们本质上是平等的。 【参考方案1】:

https://github.com/gcc-mirror/gcc/blob/master/gcc/ginclude/stddef.h

<stddef.h> 将 NULL 定义为字面意义上的 0。

使 C 中的条件语句为“真”的原因在于它不为 0。就是这样。

! 运算符将非零值转换为 0,将 0 值转换为 1。 如果操作数相等,== 运算符返回 1,否则返回 0。

你的两个陈述在逻辑上是等价的。 (可能)唯一的区别是风格或个人喜好。您可能会发现查看已编译的程序集以深入挖掘会很有趣。

【讨论】:

"<stddef.h> 将 NULL 定义为字面上的 0。" 它可能在您的系统上这样做,但它不需要我>。它只需要将它定义为一个空指针常量,它可能是一个依赖于编译器的内置函数,例如__null 这是一个公平的观点,但从程序员的角度来看,它始终为 0 - 如果不是这样,条件语句将无法在将 NULL 定义为 0 以外的值的系统上工作。 好吧,((void*)0) 在没有提供额外功能的内置函数时在 C 中也很常见(特别是,如果未在指针上下文中使用,也未与自身或其他空指针常量进行比较,则会发出警告)。 【参考方案2】:

这两者是等价的。

逻辑非运算符!在C standard的第6.5.3.3p5节中定义如下:

逻辑否定运算符! 的结果为 0,如果 其操作数的值比较不等于 0,如果其操作数的值比较不等于 1 操作数比较等于 0。结果的类型为 int表达式!E 等价于(0==E)

所以!file0 == file 相同。值 0 被认为是 空指针常量,在 6.3.2.3p3 节中定义:

值为 0 的整数常量表达式,或者这样的 转换为void * 类型的表达式称为空指针 常量.66) 如果将空指针常量转换为指针 类型,结果指针,称为空指针,保证 比较不等于指向任何对象或函数的指针

66 ) 宏 NULL (和其他头文件)中定义为空指针常量;见 7.19

这意味着将指针与 0 进行比较与将其与NULL 进行比较是相同的。所以!filefile == NULL 是一样的。

【讨论】:

值得注意的是,即使在 NULL 指针的位模式与值为 0 的整数的位模式不同的系统上,它们也是相同的(出于给出的原因)。

以上是关于if (!file) 和 if (file == NULL) 的区别的主要内容,如果未能解决你的问题,请参考以下文章

shell中判断语句if中-z 和 -n

php: if (file_exists($file)) 对某些文件返回 true,对其他文件返回 false

if(isset($_FILES)) 在 PHP 中不起作用

清除缓存 if(file_exists)

shell里面if条件判断

Shell与if相关参数