【问题标题】:C++ Instantiating "Implicit" Class ObjectC++ 实例化“隐式”类对象
【发布时间】:2015-04-07 18:08:36
【问题描述】:
class Cents
{
private:
int m_nCents;

public:
Cents(int nCents) { m_nCents = nCents; }

// Overload cCents + int
friend Cents operator+(const Cents &cCents, int nCents);
int GetCents() { return m_nCents; }
};

// note: this function is not a member function!
Cents operator+(const Cents &cCents, int nCents)
{
return Cents(cCents.m_nCents + nCents);
}

int main()
{
Cents c1 = Cents(4) + 6;
std::cout << "I have " << c1.GetCents() << " cents." << std::endl;

return 0;
}

我不清楚如何表达

Cents(4)+6 

排队

Cents c1 = Cents(4) + 6;

被评估。 是的,我知道我们分别为 Cents 和 int 类型的操作数重载了运算符“+”。

据我了解,Censt(4) 是构造函数,对吗?所以当

Cents operator+(const Cents &cCents, int nCents)
 {
 return Cents(cCents.m_nCents + nCents);
 }

被称为 cCenst 是否会成为对 Cents(4) 的引用?

从线

return Cents(cCents.m_nCents + nCents);

可以推断出 cCenst 是 Censt 类型的对象,因为我们通过成员选择运算符“。”访问 m_nCents。但是 Censt(4) 是一个构造函数,而不是一个类对象。

对我来说,cCenst 引用 Cents(4) 似乎没有意义,因为它们并不等同。

【问题讨论】:

  • 您应该减少此处的标签数量并将 c++ 标签应用于您的问题(如果这是 c++)。
  • 我看不出这个问题与运算符重载有什么关系。你为什么不能把它摆出来,因为它与某个任意函数 void foo(const Cents&amp;) 相关,用法示例是 foo(Cents(4))
  • 是的,我必须承认我的示例与运算符重载无关,而是通过引用将类对象传递给函数。然而,我不会编辑代码并删除运算符重载的东西,因为我想不出一个有意义的例子。但是考虑到您的明智言论,我将更改问题标题。
  • @MaxGreen:谢谢;现在好多了。

标签: c++ object constructor instantiation objectinstantiation


【解决方案1】:

据我了解,Censt(4) 是构造函数,对吧?

不,不完全是。你从不直接调用构造函数,即使这种语法看起来有点像你这样做。

在这里,您正在使用构造函数参数4 构造一个Censt 类型的临时对象。

你可以这样想:

Censt x(4);  // creates a `Censt` with name `x` from argument `4`
Censt(4);    // creates a `Censt` with no name from argument `4`

不是函数调用。

cCenst 会成为对 Cents(4) 的引用吗?

是的。

但是 Censt(4) 是一个构造函数,而不是一个类对象。

再次,不。它一个对象。

【讨论】:

  • 既然您告诉我 Cents(4) 创建了一个未命名的对象,我了解函数参数“cCenst”如何成为对它的引用。谢谢)
  • @MaxGreen: 没问题 :)
  • 更准确地说,Cents(4) 是一个右值表达式。正如4 是一个右值一样。
  • @KubaOber:上一层抽象,它是一个对象。两个抽象层次,它是源代码文件中的一系列字符。精确固然很好,但上下文就是一切。
  • 我只是认为将这个术语带入讨论很有用,因为很难在不区分的情况下谈论大多数现代 C++。我并不是说你不提它就大错特错了:)
【解决方案2】:

据我了解,Censt(4) 是构造函数,对吧?

Cents(4) 是一个创建Cents 对象的表达式(导致调用构造函数)。计算表达式的结果就是这样创建的对象。

那么当 [...] 被调用时,cCenst 是否会成为对 Cents(4) 的引用?

它成为对在评估 Cents(4) 子表达式时创建的对象的引用。

return Cents(cCents.m_nCents + nCents); 行可以推断出cCenst 是Censt 类型的对象,因为我们通过成员选择运算符“。”访问m_nCents。

cCentsconst Cents &amp; 类型,因为它是这样声明的。

但是 Censt(4) 是一个构造函数,而不是一个类对象。

Cents(4) 是一个表达式。它不是构造函数。详细说明:它是一个表达式,需要调用构造函数进行计算,并产生一个Cents 对象。

在表达式中:

Cents c1 = Cents(4) + 6;

首先计算子表达式(根据运算符优先级等)。因此,Cents(4) 被评估并成为Cents 对象。然后可以认为整体表达式是:

Cents c1 = &lt;a-newly-created-Cents-object&gt; + 6;

&lt;a-newly-created-Cents-object&gt; + 6 部分由 next 评估,方法是调用定义的 + 运算符。在该运算符方法中,cCents 参数成为对&lt;a-newly-created-Cents-object&gt; 的引用。

【讨论】:

    【解决方案3】:

    构造函数将创建对象,因此在您获得一个对象和一个 int 之后,它将获取该对象。 它不完全是一个引用,它是一个 const 引用,因此您不需要在之前创建它,因为无法修改对象。

    【讨论】:

    • 不,构造函数不会“返回”任何东西。
    • 是的,你说得对,这不是我要写的词。我改了。
    • 构造函数也不“创建对象”。至少,不是全部。他们初始化数据成员。内存分配和其他东西由语言单独处理。这就是不是“调用构造函数”的原因;事实上,构造函数甚至没有名字(12.1/1)!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-28
    相关资源
    最近更新 更多