这个问题来自C ++ Primer(第5版),这是第15章中模拟虚拟副本的最后一个主题。
定义两个通过继承相关的类:
class Quote{
public:
virtual Quote* clone() const & {return new Quote(*this);}
virtual Quote* clone() && {return new Quote(std::move(*this));}
//other members
};
class Bulk_quote: public Quote{
public:
Bulk_quote* clone() const& {return new Bulk_quote(*this);}
Bulk_quote* clone() && {return new Bulk_quote(std::move(*this));}
//other members
};
以及使用它们的课程:
class {
public:
void add_item(const Quote& sale) //copy the given object
{ items.insert(std::shared_ptr<Quote>(sale.clone()));}
void add_item(Quote&& sale) //move the given object
{items.insert(std::shared_ptr<Quote>(std::move(sale).clone()));}
//other memebers
private:
static bool compare(const std::shared_ptr<Quote>& lhs,const std::shared_ptr<Quote>& rhs)
{return lhs->isbn() < rhs->isbn();}
std::multiset<std::shared_ptr<Quote>,decltype(compare)*> items(compare);
};
我被困在两个观察中:
(1)为什么std::move(*this)
在成员virtual Quote* clone()&&
的定义?据我所知,这个版本只能在参考限定符&&
下的可修改的右值(例如,时间对象)上运行。可能std::move(*this)
被*this
取代?
(2)类似于(1),为什么std::move(sale)
在成员add_item
的第二个定义中,它只能在rvalue的对象上运行。对于右值参考Quote&& sale
只能绑定到右值,std::move(sale)
是否必要?
为了调用add_item
的第二个版本,该书说“尽管销售类型是右值参考类型,但销售(像任何其他变量一样)是左值”。但是,如果void add_item(const Quote& sale)
是左值,则会调用verison sale
。谁能帮助我?
你似乎混淆了表达式的对象。值类别(左值或右值)是表达式的属性,而不是对象的属性,因此,例如,即使*this
引用临时对象,它作为表达式仍然是左值。 sale
也是如此。
有一些复杂的规则来确定表达式是左值还是左值。您的示例的相关规则是:
*expr
的表达总是一个左值;