2017-11-11 185 views
6

我了解左值的几件事数组,但我不明白下面的代码是如何给出一个错误:为什么foo((&i)++)给出左值需要的错误。有没有相关的

#include<stdio.h> 

void foo(int *); 

int main() 
{ 
    int i=10; 
    foo((&i)++); 
} 

void foo(int *p) 
{ 
    printf("%d",*p); 
} 

6:13:错误:需要左值的递增操作数 FOO(( & i)++); ^

+3

由于'&i'不是*左值*以及''++操作者需要一个。这大致相当于'&i = &i + 1;',最后一个表达式对你有意义吗? –

+1

使用变量'i'是一个左值。如果你有像'int * p =&i;'这样的指针,那么'p'也是一个左值。但'&我'本身*不是*左值。也许你会对[这个值类别参考]感兴趣(http://en.cppreference.com/w/c/language/value_category)?请注意,[非左值表达式列表](http://en.cppreference.com/w/c/language/value_category#Non-lvalue_object_expressions)包含“地址 - 运算符”。 –

+0

可能重复[左值需要作为增量操作数](https://stackoverflow.com/questions/3364445/lvalue-required-as-increment-operand) – ssharma

回答

2

x ++以下步骤的结果。

1) read the value of x in to register. 
2) increment the value of x 
3) write the incremented value back to x (which means you are changing the value of x by '1') 

但是你正在尝试做的是(& I)++,这意味着以下。

1) read address of i into register 
2) increment the address by 1 
3) write the incremented value in to address again? How you can change the address? 

如果要将存储在下一个地址中的整数发送到foo(),则需要按如下方式增加。

int *p = &i + 1; 
foo(p); 

但是,这可能会导致未定义的行为,因为你只知道我存储的值的地址。一旦你增加地址,你会得到下一个地址,它可能包含一些垃圾值。

1

试图将一元运算符&应用于临时对象,该临时对象的计算结果为表达式(&i)++。您不得将操作员应用于临时对象。

C标准(6.5.3.2地址和间接运算符):

1 The operand of the unary & operator shall be either a function designator, the result of a [] or unary * operator, or an lvalue that designates an object that is not a bit-field and is not declared with the register storage-class specifier.

+1

“*尝试将一元运算符'&应用于临时对象... *”确定? '&'适用于'i'。对我来说,看起来好像你混淆了'&'和'++'。 – alk

相关问题