c语言 error c2106: "=": 左操作数必须为左值,错误C2106: '=':左操作数必须为l值。

5

The message says that you try to assign to an expression which is not an lvalue. For built-in types, you can only assign to lvalues (that's where the name comes from: lvalue = value that can be on the left hand side of the assignment operator, while rvalue = value that must be on the right hand side of the assignment operator).

消息说,您试图分配一个不是lvalue的表达式。对于内置类型,您只能分配给lvalues(这就是名称的来源:lvalue =赋值操作符左边的值,而rvalue =赋值操作符右边的值)。

So what is an lvalue or an rvalue? Consider the following code:

那么什么是lvalue或rvalue呢?考虑下面的代码:

int a;

a = 3;

In this assignment a is an lvalue (if it weren't, the compiler would complain). That is, the expression a refers to an object which can be modified. On the other hand, 3 is an rvalue, that is, basically a value. Of course you cannot assign to 3; the compiler would complain about the statement 3=a; with exactly the same message you got in your code.

在这个任务中,a是一个lvalue(如果不是的话,编译器会抱怨)。也就是说,表达式a是指可以修改的对象。另一方面,3是一个rvalue,也就是一个值。当然你不能分配到3;编译器会抱怨语句3=a;与你在代码中得到的信息完全相同。

So as a first approximation, an lvalue designates an object, while an rvalue designates a value. Note that this is also true for assignment of the form

因此,作为第一个近似,一个lvalue指定一个对象,而一个rvalue指定一个值。注意,这也适用于表单的赋值。

a = b;

where b also is a variable. What happens here is the so-called lvalue to rvalue conversion: What is assigned is not the object b, but its current value.

b也是一个变量。这里发生的是所谓的lvalue到rvalue转换:所分配的不是对象b,而是它的当前值。

Now consider the following case:

现在考虑以下情况:

int f();

f() = 3;

Here you might argue that the function f does return an object (if you use some user-defined type, you even can see its construction/destruction). But the compiler still complains with the message you got. Why?

在这里,您可能会认为函数f返回一个对象(如果您使用一些用户定义的类型,您甚至可以看到它的构造/销毁)。但是编译器仍然在抱怨你得到的消息。为什么?

Well, even if you consider f to return an object, it is a temporary object which will go away immediately. So it does not make much sense to assign a value because you cannot do anything with it anyway afterwards.

即使你考虑f返回一个对象,它也是一个暂时的对象,它会立即消失。因此,分配一个值是没有意义的,因为无论如何你都不能做任何事情。

Therefore here's the second rule:

所以这是第二条规则:

Whenever there's an expression which produces a temporary object, C++ defines that expression as rvalue.

每当有一个表达式产生一个临时对象时,c++将表达式定义为rvalue。

And now we come to the definition of MyVector::at() which you did not show, but which, according to the error message, probably looks similar to this:

现在我们来定义MyVector::at()你没有显示,但根据错误信息,它可能看起来类似于:

template

T MyVector::at(int i)

{

return data[i];

}

This has essentially the same form as f above, as it also returns a T (an employee* in your case). This is why the compiler complains.

这与上面的f基本相同,因为它也返回T(在您的例子中是employee*)。这就是编译器抱怨的原因。

And that complaint is helpful: Even if the compiler wouldn't complain, the code would not dio what you almost certainly intended. The return statement returns a copy of the object data[i]. Thus if the statement payment.at(i)=NULL; had compiled, what would actually happen would be the following:

这样的抱怨是有帮助的:即使编译器不会抱怨,代码也不会显示出你的意图。return语句返回对象数据的副本[i]。因此,如果报表支付。at(i)=NULL;如果已经编译,实际发生的情况如下:

The internal object data[i] (or however you called it in your code) is copied and the temporary copy returned.

内部对象数据[i](或者您在代码中调用它)被复制,而临时副本返回。

The statement assigned that temporary copy, but leaves the original object in MyVector unchanged.

该语句指定了临时副本,但在MyVector中保留原始对象不变。

The temporary copy gets destructed, leaving no trace of your assignment.

临时拷贝被破坏,没有留下任何作业的痕迹。

This is almost certainly not what you wanted. You wanted to change the internal object. To do so, you have to return a reference to that object. A reference refers to the object it was initialized with instead of making a copy. Correspondingly, a reference, even when returned, is an lvalue (since C++11 there's a second type of reference which behaves differently, but we don't need to care about that here). Your corrected function then reads

这几乎肯定不是你想要的。你想要改变内部对象。为此,必须返回对该对象的引用。引用是指它被初始化而不是复制的对象。相应地,引用,即使返回时,也是一个lvalue(因为c++ 11有第二种类型的引用,它的行为是不同的,但是我们不需要关心这里)。你的修正函数然后读取。

template

T& MyVector::at(int i)

{

return data[i];

}

and with that definition, payment.at(i)=NULL; not only compiles, but actually does what you want: Change the internally stored i-th pointer in payment to NULL.

用这个定义,支付。at(i)=NULL;不仅编译,而且实际上做了您想要的:将内部存储的i-th指针更改为NULL。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值