我遇到了这段代码:
void f(const std::string &s);
然后打个电话:
f( *((std::string*)NULL) );
我想知道其他人对这种结构的看法,它用于表示函数f()应该使用一些默认值(它计算)而不是一些用户提供的值.
我不知道该怎么想,它看起来很奇怪,但你觉得这个结构怎么样?
不.它是未定义的行为,可以导致代码执行任何操作(包括重新格式化硬盘,核心转储或侮辱您的母亲).
如果您需要能够传递NULL,那么使用指针.采用引用的代码可以假定它引用有效对象.
增编:C++ 03标准(ISO/IEC 14882,2 次版2003)称,在§8.3.2 "参考",第4款:
应初始化引用以引用有效的对象或函数.[ 注意:特别是,在明确定义的程序中不能存在空引用,因为创建这样的引用的唯一方法是将它绑定到通过解引用空指针获得的"对象",这会导致未定义的行为.如9.6中所述,引用不能直接绑定到位字段.]
[大胆添加强调]
你有时会在相当深奥的模板库代码中看到这样的结构,但只能sizeof()
在它无害的地方.
假设您想知道函数类型的返回类型的大小,F
如果它传递了对类型的引用T
作为参数(两者都是模板参数).你可以写:
sizeof(F(T()))
但是,如果T恰好没有公共默认构造函数呢?所以你这样做:
sizeof(F(*((T *)0)))
传递给sizeof
永远不会执行的表达式- 它只是被分析到编译器知道结果大小的程度.
我很好奇 - 函数'f'实际检查这个条件吗?因为如果它没有,并且它试图使用该字符串,那么当你尝试使用它时,这显然会崩溃.
如果'f'检查引用是否为NULL,那么为什么不只是使用指针?是否有一些硬性和快速的规则,你不会使用指针和一些傻瓜遵守法律的字母,而不考虑它的含义?
我只想知道......