你什么时候能够返回NULL作为C函数的返回值?
我想知道你是否可以告诉我你什么时候能够返回NULL
,这是C中函数的结果。
例如, int lenght()
不能返回NULL
因为在return语句中需要一个int
。
但是函数struct node* find(int key)
,当使用链表时允许我返回NULL。
NULL
是指针值 – 或者更确切地说是空指针值。
NULL
表示函数无法找到指针应指向的位置 – 例如,如果要打开文件,但它不起作用,则文件指针将返回为NULL
。 因此,您可以测试指针的值并检查它是否有效。
如果你正在写一个例程
int length()
然后你可以返回一个负值,如果长度无法读取你发送它的长度 – 这将是一种指示错误的方式,因为通常长度永远不会是负面的….
这是一个惯例问题 ,你应该清楚地掌握一个并记录下来(至少在评论中)。
有时指针确实应该总是指向一个有效的地址(参见这个 intSwap
示例,两个参数都应该是有效的指针)。 在其他时候,它应该是这样一个有效的地址,或者是NULL
。 从概念上讲,指针类型按照惯例是一种求和类型 (在真正的指针地址和特殊的NULL
值之间)。
请注意,C语言没有强制某些给定指针始终有效且非空的类型(或符号)。 顺便说一句,特别是GCC,你可以用__attribute__
使用nonnull
空来注释一个函数来表示给定的参数永远不会为空。
一个典型的例子是FILE*
指针。 记录fopen
函数能够返回NULL
(失败时)或一些有效指针。 但是fprintf
函数期望一个有效的指针(并将NULL
传递给它,因为第一个参数是一些未定义的行为 ,通常是一个分段错误 ;而UB非常糟糕 )。
一些非可移植程序甚至使用几个“特殊”指针值(不应该取消引用),例如(在Linux / x86-64上) #define SPECIAL_SLOT (void*)((intptr_t)-1)
(我们知道在Linux它永远不是一个有效的地址)。 然后我们可以有一个约定,指针是指向有效内存区域的有效指针,或NULL
或SPECIAL_SLOT
(因此,如果被视为抽象数据类型 ,它是两个不同的无效指针的总和类型NULL
和SPECIAL_SLOT
和集合有效地址)。 另一个例子是MAP_FAILURE
,它是Linux上mmap(2)的结果。
顺便说一句,当使用C中的指针来堆积分配的数据(通过malloc
间接获得)时,您还需要有关谁负责释放数据的约定(通过使用free
,通常通过提供的函数来释放数据及其所有内部资料) )。
好的C编程需要许多关于指针的明确约定 ,并且必须精确地理解它们并将它们很好地记录下来。 在GTK中查找示例[s]。 另请阅读restrict
。
什么时候能够返回NULL作为C函数的返回值
通常,当且仅当函数返回指针类型时:
T * function( | void>); /* With T being any valid type. */
还有其他的极端情况,这取决于使用中的C实现。
NULL
绝对是一个指针。 因此,如果您的函数需要返回指针并且由于某种原因不能,则应返回明显的“无效指针”,即NULL。
NULL可以定义为0或(void *)0 (参见6.3.2.3p3和7.19p3 )。
因此,它可能总是在返回指针类型的函数中用作返回值,并且根据实现,它可能可用作返回数值类型的函数中的返回值,尽管后者是个坏主意,因为预期为NULL
与指针结合使用。