Ric*_*ick 52 c++ const reference language-lawyer
我正在阅读一本书的代码片段并找到:
const char* const & a = "hello"; //can compile
const char*& a = "hello"; //cannot
Run Code Online (Sandbox Code Playgroud)
我所知道的是,在初始化引用时,不会发生数组到指针的转换.
const char* const &,const pointer对指针的引用,指针指向const char.
const char*&,pointer对指针的引用,指针指向
const char.
那么为什么添加一个额外的const,指示指针是a const,允许它编译?
Sto*_*ica 37
它基本上坚持这个公式
T const & a = something_convertible_to_T;
Run Code Online (Sandbox Code Playgroud)
T是哪里const char*.在第一种情况下,可以实现临时指针,分配文字的地址,然后将其自身绑定到引用.在第二种情况下,由于左值引用不是常量,因此不会发生.另一个例子更多相同
const char* && a = "hello"; // rvalue ref makes a no into a yes.
Run Code Online (Sandbox Code Playgroud)
现在,临时指针绑定到右值引用.
在阅读了@StoryTeller的精湛答案之后,还有一些额外的措辞,因为我不得不经历一个不同的思考过程.
所以语法,在两条线我们定义了一个参考 a,而在这两个我们将有一个物化一的临时指针,是以地址字符串字面量.两者之间的唯一区别是第二个const只出现在这里:
const char* const & a = "hello";
Run Code Online (Sandbox Code Playgroud)
而不是在这里:
const char*& a = "hello";
Run Code Online (Sandbox Code Playgroud)
第2个const表示此处引用的对象(在这种情况下是指针)本身就是const,因为它不能使用此引用进行修改.
因此,因为这个字符串文字的类型是(而不是例如),我们对第二行中的类型的引用不能绑定到它 - 但是第一行中的引用是对类型的引用.为什么?由于参考初始化规则:const char[6]const char *lvalueconst char*const char* const
(5)类型"cv1 T1"的引用由类型"cv2 T2"的表达式初始化如下:
(5.1)如果引用是左值引用和初始化表达式
- (5.1.1)是左值(但不是位域),"cv1 T1"与"cv2 T2"参考兼容,[...]
- (5.1.2)有一个类类型(即T2是类类型)[...]
两个表达式都是左值,但是我们的"cv1 T1"与我们的"cv2 T2" 不是引用兼容的,而"T2"不是类类型.
- (5.2)否则,如果引用是对非const限定类型或波动限定类型的左值引用,则程序格式错误
引用确实不是 const限定的:我们的"T1"是指向constconst char*的指针,而不是const指针.这里的实际类型是指针类型,所以这才是最重要的.
第二行的Clang错误(请仔细阅读)告诉我们:
error: non-const lvalue reference to type 'const char *' cannot bind to a value of unrelated type 'const char [6]'
const char*& a = "hello";
^ ~~~~~~~
Run Code Online (Sandbox Code Playgroud)
关于非常量左值引用的部分恰好是5.2 - 在我们的例子中,左值是一个指针const,但它本身不是常量!与第一行不同.关于绑定到不相关类型的部分恰好是5.1 - 我们与RHS const char*不兼容const char[6],或者const char* const在数组到指针转换之后.
由于这个确切的原因,或缺乏它,这可以编译无错误:
char* const & a = "hello";
Run Code Online (Sandbox Code Playgroud)
除了ISO C++ 11警告之外,编译器允许这一个传递(不是它应该,因为字符串文字是'const char 6 '而我们不应该首先删除它const),因为现在引用是const关于它的对象,指针.
另一个有趣的事情是,一个rvalue引用const char* && a (没有"第二个const")可以绑定到从字符串文字中实现的临时指针,就像@StoryTeller自己提供的那样.这是为什么?由于数组到指针转换的规则:
可以将"N T数组"或" T的未知边界数组"类型的左值或右值转换为"指向T的指针" 的prvalue.
在这里没有提及const或其他cv资格的措辞,但只有在我们初始化rvalue ref时才会这样.
| 归档时间: |
|
| 查看次数: |
2890 次 |
| 最近记录: |