复合文字中使用的强制转换与指针变量上使用的强制转换之间的区别?
考虑以下代码:
int main()
{
int *p;
++((int){5}); //compile without err/warning
&((int){5}); //compile without err/warning
++((char *)p); //Compile-time err: invalid lvalue in increment
&((char *)p); //Compile-time err: invalid lvalue in unary '&'
}
为什么复合文字在这里不会生成错误?
Consider the following code:
int main()
{
int *p;
++((int){5}); //compile without err/warning
&((int){5}); //compile without err/warning
++((char *)p); //Compile-time err: invalid lvalue in increment
&((char *)p); //Compile-time err: invalid lvalue in unary '&'
}
Why do the Compound Literals do not generate errors here?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
这是因为复合文字中的“强制转换”根本不是强制转换 - 它只是看起来像强制转换。
复合文字(完整的构造
(int){5}
)创建一个左值。然而,与大多数其他运算符一样,强制转换运算符仅创建右值。这个例子是允许的(但没用,就像你的
int
例子一样):It is because the "cast" in a compound literal is not a cast at all - it just looks like one.
A compound literal (which is the complete construction
(int){5}
) creates an lvalue. However a cast operator creates only an rvalue, just like most other operators.This example would be allowed (but useless, just like your
int
examples):复合文字中没有强制转换。复合文字的
(int)
部分不是强制转换。它只是复合文字语法的类型部分。因此,这种情况下的问题是复合文字是否是一个对象,即左值。答案是肯定的,复合文字就是左值。因此,您可以对其应用任何需要左值的运算符(例如++
或&
)。示例的第二部分包含强制转换。强制转换的结果始终是右值。您不能将
++
和&
与右值一起使用。Compound literal doesn't have a cast in it. The
(int)
part of your compound literals is not a cast. It is just a type part of compound literal syntax. So, the question in this case is whether a compound literal is an object, an lvalue. The answer is yes, a compound literal is an lvalue. For this reason you can apply any operators to it that require an lvalue (like++
or&
).The second part of your example contains casts. The result of a cast is always an rvalue. You can't use
++
and&
with rvalues.复合文字中的“强制转换”实际上不是强制转换,而是复合文字的类型。
因此,
(int){5}
确实更像是一个匿名int
,因此是一个有效的lvalue
,可以在该对象的任何地方使用可以使用相同的类型(在本例中为int
)。而
(char *)p
实际上是一个 cast (rvalue
),因此它不能递增++
或引用&
。阅读 Dr.Doobs 关于复合文字的深入文章。
The "cast" in a compound literal is actually not a cast, rather it is the type of the compound literal.
So,
(int){5}
is indeed more like an anonymousint
, hence a validlvalue
which can be used anywhere an object of the same type (int
in this case) could be used.Whereas,
(char *)p
is actually a cast (rvalue
), so it cannot be incremented++
or referenced&
.Read Dr.Doobs's in-depth article about compound literals.