【问题标题】:Why do I an get error when trying to print a null pointer为什么在尝试打印空指针时出现错误
【发布时间】:2019-08-03 01:44:45
【问题描述】:
#include <stdio.h>
void main ()
{
    int* p = NULL;
    printf("%d", *p);
}

打印出来:

Exception thrown: read access violation.
p was nullptr.

【问题讨论】:

  • 您没有打印空指针,而是打印到它指向的位置。你不能用空指针来做。尝试打印 p 而不是 *p。此外,使用%p 打印指针,而不是%d
  • OT:至少必须是int main(),或者更好的是int main(void)

标签: c pointers


【解决方案1】:

NULL 指针不能被取消引用。

这样做会调用undefined behavior,在本例中表现为您的程序崩溃。

这在C standard 的第 6.5.3.2p4 节中有记录:

4 一元 * 运算符表示间接。如果操作数指向一个函数,则结果是一个函数指示符;如果它指向一个 对象,结果是一个指定对象的左值。如果 操作数的类型为“类型指针”,结果为 键入“类型”。 如果分配了无效值 指针,一元的行为 * 运算符未定义。 102)

102) 因此,&amp;*E 等价于 E(即使 E 是空指针),并且 &amp;(E1[E2])((E1)+(E2))。如果E 是一个 函数指示符或作为有效操作数的左值 一元 &amp; 运算符, *&amp;E 是函数指示符或等于 E 的左值。如果 *P 是左值,T 是对象指针类型的名称, *(T)P 是一个左值,其类型与T 指向的类型兼容。

在取消引用指针的无效值中 由一元 * 操作符是一个空指针,一个与指向的对象类型不恰当对齐的地址,以及后面的对象地址 生命的尽头。

如果要打印指针本身,请将其传递给 printf 而不取消引用,并使用 %p 格式说明符:

printf("%p\n", (void *)p);

【讨论】:

  • 为了完整性:对于这个“NULL 指针可能不会被取消引用”的重要规则,通常存在例外。当 sizeof 运算符应用于它时,可能会取消引用“无效”指针。例如做size_t size_of_int = sizeof *((int*) NULL); 是有效的。
【解决方案2】:

int* p = NULL; *p; 的行为是未定义

如果要打印出p地址,则使用"%p" 作为格式说明符,并删除取消引用:

printf("%p", (void*)p);

为了完全匹配格式说明符,需要转换为(void*)

【讨论】:

    猜你喜欢
    • 2016-09-01
    • 1970-01-01
    • 2022-01-08
    • 1970-01-01
    • 1970-01-01
    • 2021-11-13
    • 1970-01-01
    • 2020-11-13
    • 1970-01-01
    相关资源
    最近更新 更多