【问题标题】:what are l-value and r-value expression?什么是左值和右值表达式?
【发布时间】:2014-08-10 05:33:29
【问题描述】:

pre ++、post ++ 和 * 的优先顺序是什么?这些表达式在 VS 08 编译器中是如何解析的。

 void main(){
        int arr[] ={34,11,43};
        int *ptr = arr;
        printf("%d",++*ptr++);
        printf("%d",++ptr++);
 }

解释 l 值表达式。我想了解为什么 ++*ptr++ 是一个有效的表达式,而 ++ptr++ 给出错误。

error: '++' needs l-value

【问题讨论】:

    标签: c lvalue rvalue


    【解决方案1】:

    优先级分别为++(*(ptr++))++(ptr++)

    ptr++ 是一个右值,因为语言定义是这样说的。 (rvalue 表示您可以使用该值,但不能尝试引用可能存储该值的内存位置)。

    ++ 运算符更新存储在内存位置的值,因此它只能应用于左值。所以++(ptr++) 是违反约束的。

    但是,* 可以应用于右值,结果是左值(即指定内存位置的表达式)。所以++可以应用于*ptr++

    【讨论】:

    • ptr+1 也是一个右值,“因为语言定义是这样说的”,但除此之外还有更多......不是取消引用的表达式作为目标没有意义一个值。
    • 这个语句打印什么?--> printf("%d",++*ptr++); 35 还是 12?
    • @piyukr 算出你认为应该打印的内容,然后试试看
    【解决方案2】:
    ++p++
    

    说:前增量p 和后增量p(未指定顺序)。即使它被允许,由于modifying p more than once before encountering a sequence point,它也会调用未定义的行为。

    无论如何,增量运算符,后置和前置,返回一个rvalue。右值是表达式的值。它没有可写入的位置,可以被认为是一个中间值。

    *p++
    

    这个表达式最初产生一个左值*p。可以写入该位置,因此它按预增量递增,然后 p 本身递增。增量会产生一个右值,但您并没有尝试修改它。

    【讨论】:

    • 我想了解为什么 ++*p++ 有效而 ++p++ 无效
    • "++p++ 说:前增量 p 和后增量 p(未指定顺序)" - 这是错误的。请参阅马特麦克纳布的回答。 “这个表达式最初产生一个右值,*p”——*p 是一个左值。 “然后 p 本身增加。增量返回一个右值”——这是荒谬的;增量是一个副作用,它不会“返回”任何东西,并且可能在序列点之前不会发生。
    • 进一步:“这个表达式最初产生一个右值,*p”——不,它产生*p的内容,它被传递给printf。表达式和它们产生的值是不同的东西。
    【解决方案3】:

    在 C 编程中,前置增量和前置减量运算符返回一个右值,它本质上告诉您它是一个结果,而不是进行赋值的地方。在 C++ 编程中,前置增量和前置减量运算符返回一个左值,您可以在其中执行进一步的赋值。

    这样的陈述,

    int i=10;
    ++i=5;
    

    在 C++ 中语法上有效。但在 C 中,这是一个语法错误。

    即使在 C++ 中,postincrement 和 postdecrement 运算符也会返回一个右值。因此,以下语句在 C 和 C++ 中都会出现语法错误。

    int i=10;
    i++=5;
    

    【讨论】:

    • "++i=5; 在 C++ 中语法上有效" -- 但毫无意义,因为 ++= 取代,导致 i 为 5。
    猜你喜欢
    • 1970-01-01
    • 2020-01-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-11-20
    • 2015-02-06
    • 1970-01-01
    相关资源
    最近更新 更多