简体   繁体   English

比较运算符与三向运算符的嵌套生成?

[英]Nested generation of comparison operator with three-way operator?

Consider the following two overload operator<=> for S :考虑S的以下两个重载operator<=>

#include <compare>

struct S {};

int operator<=>(S, int) { return 0;  } #1
S   operator<=>(S,   S) { return {}; } #2

If I compare an object S with an int , the #1 will generate the right operators for me, so expression like S{} <= 0 , 0 < S{} or 0 <=> S{} would be just fine .如果我将object Sint进行比较, #1将为我生成正确的运算符,因此像S{} <= 00 < S{}0 <=> S{}这样的表达式就可以了。

But if I compare an object S with other object S :但是,如果我将 object S与其他 object S进行比较:

S{} < S{};

Then this will be rewritten as (S{} <=> S{}) < 0 .然后这将被重写为(S{} <=> S{}) < 0 Since (S{} <=> S{}) will return an other S , we back to the origin problem: S compare with a int .由于(S{} <=> S{})将返回另一个S ,我们回到原点问题: Sint进行比较。 At this time, we don't have operator<(S, int) , so #1 would generate the right operator for me.目前,我们没有operator<(S, int) ,所以#1会为我生成正确的运算符。

But surprisingly, none of the three compilers do this to me.但令人惊讶的是,三个编译器都没有对我这样做。 GCC, Clang, and MSVC all reject S{} < S{} with the same error message: GCC、Clang 和 MSVC拒绝S{} < S{}并显示相同的错误消息:

no match for 'operator<' (operand types are 'S' and 'int')

This makes me frustrated.这让我很沮丧。 Since the #1 actually exists.因为#1确实存在。 Why the nested generation of the operator are not occurring here?为什么这里没有发生操作符的嵌套生成? What does the standard say?标准是怎么说的? Is there a static constraint violation?是否存在 static 约束违规?

This is ill-formed, although admittedly the error message is quite confusing.这是格式错误的,尽管错误消息确实令人困惑。

The rule, from [over.match.oper]/8 is (emphasis mine):来自[over.match.oper]/8的规则是(强调我的):

If a rewritten operator<=> candidate is selected by overload resolution for an operator @ , x @ y is interpreted as 0 @ (y <=> x) if the selected candidate is a synthesized candidate with reversed order of parameters, or (x <=> y) @ 0 otherwise, using the selected rewritten operator<=> candidate.如果通过重载决策为运算符@选择了重写的operator<=>候选者,如果所选候选者是具有相反参数顺序的合成候选者,则x @ y被解释为0 @ (y <=> x) ,或者(x <=> y) @ 0否则,使用选定的重写operator<=>候选。 Rewritten candidates for the operator @ are not considered in the context of the resulting expression.在结果表达式的上下文中不考虑运算符@的重写候选。

The expression S{} < S{} is going to resolve to the rewritten candidate (S{} <=> S{}) < 0 .表达式S{} < S{}将解析为重写后的候选(S{} <=> S{}) < 0 The resulting expression will not consider rewritten candidates in its lookup.生成的表达式在其查找中不会考虑重写的候选者。 So when we do S{} < 0 , that is going to look for just an operator< , and not also operator<=> .因此,当我们执行S{} < 0时,将查找operator< ,而不是operator<=> It can't find such a thing, so the expression is ill-formed.它找不到这样的东西,所以表达式是不正确的。

<source>:8:14: error: no match for 'operator<' (operand types are 'S' and 'int')
    8 | auto x = S{} < S{};
      |          ~~~~^~~~~

In that sense, the error is literally true: there is no match for, specifically operator< with those operands.从这个意义上说,错误是真的:没有匹配,特别是operator<与这些操作数。 Although it would help if the error message had quite a bit more context explaining why it's looking for that (and I submitted a request to that effect in 99629 ).虽然如果错误消息有更多的上下文来解释它为什么要寻找它(并且我在99629中提交了一个请求),这会有所帮助。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 三向比较运算符总是有效吗? - Is the three-way comparison operator always efficient? 顺序推导不一致的三向比较算子 - Three-way comparison operator with inconsistent ordering deduction C++ 中的 &lt;=&gt;(“宇宙飞船”,三路比较)运算符是什么? - What is the <=> ("spaceship", three-way comparison) operator in C++? 三向比较运算符与减法有何不同? - How is the three-way comparison operator different from subtraction? 为什么默认三通运算符(spaceship &lt;=&gt;)生成相等运算符(==)而用户定义三通运算符不? - Why default three-way operator (spaceship <=>) generates equality operator (==) and user define three-way operator not? 三向比较运算符成员与非成员实现 - Three-way comparison operator member vs non-member implementation 将三路比较运算符的结果与 nullptr 进行比较有什么作用? - What does comparing the result of the three-way comparison operator with nullptr do? 如何使用三路比较(spaceship op)实现不同类型之间的operator==? - How to use three-way comparison (spaceship op) to implement operator== between different types? 为什么要使用三向比较运算符 (&lt;=&gt;) 而不是双向比较运算符? 这有优势吗? - Why should I use the three-way comparison operator (<=>) instead of the two-way comparison operators? Does this have an advantage? 三路运算符 &lt;=&gt; 隐式转换返回结构 function - Three-way operator <=> return struct with implicit conversion function
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM