【问题标题】:Precedence while overloading operators C++重载运算符时的优先级 C++
【发布时间】:2015-01-29 17:13:07
【问题描述】:

我有一个类,其中我重载了一些运算符。我的代码是这样的:

myClass << 12 << 14 << 21 << 44

这很好用,首先运行myClass &lt;&lt; 12,然后运行myClass &lt;&lt; 14

但如果我尝试做这样的事情,我会遇到问题:

myClass << 12 << 14+18 << 36 << 14 << 47

运算符+ 也重载了,问题是14+18myClass &lt;&lt; 12 之前运行。我真的需要先执行myClass &lt;&lt; 12,然后再执行14+18。我怎样才能做到这一点?

编辑:

我想将一些数字和数字数组放入流中。数字部分解决了。至于数字数组,我正在做这样的事情:

myClass << 12 << myClass(array,10) << 21 << 19

其中运算符() 被重载,array 是数字数组,10 是数组的长度。我这样做是因为我需要某种方法来保持数组的长度,但问题是 myClass(array,10)myClass &lt;&lt; 12 之前执行。所以,在这种情况下,我想首先将12 放入流中,然后放入我的数字数组,我需要知道它的长度。

而且,我不想使用这个解决方案:

myClass << 12
myClass << myClass(array,10)

因为我想将我的代码用作库,所以我的意图是最终用户可以灵活地在一行中编写所有内容。

【问题讨论】:

  • 你不能为两个整数重载operator+。您的真实代码是什么样的?
  • 是的,很抱歉,我没有像那样使用 operator+。这只是一个例子。
  • 您是否尝试过使用括号强制评估顺序?如myClass &lt;&lt; 12 &lt;&lt; (14 + 18) &lt;&lt; 36 &lt;&lt; 14 &lt;&lt; 47。这是输出到标准流时建议的编码风格。
  • 为什么先执行myClass(array,10)会出问题?那个构造函数做了什么
  • @Mooing Duck 这不是构造函数(我一开始也认为它也是,直到我重读了大约 3-4 次问题),它是 operator() 并且可能不是返回表示数组的字符串它立即写入流。

标签: c++ operators overloading operator-precedence


【解决方案1】:

好的,让我们简化并分解这里发生的事情。您调用的第一部分的计算结果如下:

myClass &lt;&lt; 12 &lt;&lt; myClass(array,10) 变成 myClass.operator&lt;&lt;(12).operator&lt;&lt;(myClass(array, 12),当名义上拼写出隐含的 this 参数时,变成类似于 operator&lt;&lt;(operator&lt;&lt;(myClass, 12), myClass(array, 10))

现在标准中关于operator&lt;&lt;(myClass, 12)myClass(array, 10) 的执行顺序的唯一说明是,两者都将在最外层的operator&lt;&lt; 被调用之前执行。在您的情况下,它选择首先执行operator()

现在,我们如何实现您想要的结果?首先,您可以将单个语句的各个部分放入多个语句中以强制执行您想要的顺序。

或者,您可以完全不同地处理数组。我建议使用format_array 函数:

std::string format_array(array, 10)
{
    // Do stuff
    return string representation of array
}

myClass << 12 << format_array(array,10) << 21 << 19

基于不同问题措辞的原始答案: 既然你不能超载operator+(int, int),我的心理问题阅读技巧告诉我,你的班级既有operator&lt;&lt;operator+,而且operator+ 是你班上的某种状态操纵器,你想将 12 和 14 插入流中后发生。

在那种情况下......不要那样做。这不是 operator+ 的用途,也不是标准流使用操纵器的原因。

但如果你绝对坚持:(myClass &lt;&lt; 12 &lt;&lt; 14) +18 &lt;&lt; 36 &lt;&lt; 14 &lt;&lt; 47

【讨论】:

  • 谢谢。我已经编辑了我的问题。希望得到更好的解释。
【解决方案2】:

您遇到了sequence points 的问题。如果您想以有保证的顺序运行插入,则必须使用

myClass << 12;
myClass << 14+18;
myClass << 36;
myClass << 14;
myClass << 47;

【讨论】:

  • 不行,因为函数参数必须在函数被调用之前计算出来。
  • 谢谢,但我不想那样做。我想将我的代码用作库,因此我希望最终用户能够灵活地在一行中编写所有代码。
猜你喜欢
  • 2017-07-27
  • 2012-10-08
  • 2013-02-24
  • 2017-06-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-03-29
相关资源
最近更新 更多