tmp/tmp4hora958/{from.md → to.md}
RENAMED
|
@@ -5,36 +5,54 @@ equality-expression:
|
|
| 5 |
relational-expression
|
| 6 |
equality-expression '==' relational-expression
|
| 7 |
equality-expression '!=' relational-expression
|
| 8 |
```
|
| 9 |
|
| 10 |
-
The `==` (equal to) and the `!=` (not equal to) operators
|
| 11 |
-
|
| 12 |
-
|
| 13 |
-
|
| 14 |
-
|
| 15 |
-
|
| 16 |
-
and only if they are both null, both point to the same function, or both
|
| 17 |
-
represent the same address ([[basic.compound]]).
|
| 18 |
|
| 19 |
-
|
| 20 |
-
|
| 21 |
-
|
| 22 |
-
|
| 23 |
-
|
| 24 |
-
|
| 25 |
-
|
| 26 |
-
cv-qualification signature ([[conv.qual]]) that is the union of the
|
| 27 |
-
cv-qualification signatures of the operand types. this implies that any
|
| 28 |
-
pointer to member can be compared to a null pointer constant. If both
|
| 29 |
-
operands are null, they compare equal. Otherwise if only one is null,
|
| 30 |
-
they compare unequal. Otherwise if either is a pointer to a virtual
|
| 31 |
-
member function, the result is unspecified. Otherwise they compare equal
|
| 32 |
-
if and only if they would refer to the same member of the same most
|
| 33 |
-
derived object ([[intro.object]]) or the same subobject if they were
|
| 34 |
-
dereferenced with a hypothetical object of the associated class type.
|
| 35 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 36 |
``` cpp
|
| 37 |
struct B {
|
| 38 |
int f();
|
| 39 |
};
|
| 40 |
struct L : B { };
|
|
@@ -45,13 +63,22 @@ int (B::*pb)() = &B::f;
|
|
| 45 |
int (L::*pl)() = pb;
|
| 46 |
int (R::*pr)() = pb;
|
| 47 |
int (D::*pdl)() = pl;
|
| 48 |
int (D::*pdr)() = pr;
|
| 49 |
bool x = (pdl == pdr); // false
|
|
|
|
| 50 |
```
|
| 51 |
|
| 52 |
-
|
| 53 |
-
`
|
| 54 |
|
| 55 |
-
|
| 56 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 57 |
|
|
|
|
| 5 |
relational-expression
|
| 6 |
equality-expression '==' relational-expression
|
| 7 |
equality-expression '!=' relational-expression
|
| 8 |
```
|
| 9 |
|
| 10 |
+
The `==` (equal to) and the `!=` (not equal to) operators group
|
| 11 |
+
left-to-right. The operands shall have arithmetic, enumeration, pointer,
|
| 12 |
+
or pointer to member type, or type `std::nullptr_t`. The operators `==`
|
| 13 |
+
and `!=` both yield `true` or `false`, i.e., a result of type `bool`. In
|
| 14 |
+
each case below, the operands shall have the same type after the
|
| 15 |
+
specified conversions have been applied.
|
|
|
|
|
|
|
| 16 |
|
| 17 |
+
If at least one of the operands is a pointer, pointer conversions (
|
| 18 |
+
[[conv.ptr]]) and qualification conversions ([[conv.qual]]) are
|
| 19 |
+
performed on both operands to bring them to their composite pointer type
|
| 20 |
+
(Clause [[expr]]). Comparing pointers is defined as follows: Two
|
| 21 |
+
pointers compare equal if they are both null, both point to the same
|
| 22 |
+
function, or both represent the same address ([[basic.compound]]),
|
| 23 |
+
otherwise they compare unequal.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 24 |
|
| 25 |
+
If at least one of the operands is a pointer to member, pointer to
|
| 26 |
+
member conversions ([[conv.mem]]) and qualification conversions (
|
| 27 |
+
[[conv.qual]]) are performed on both operands to bring them to their
|
| 28 |
+
composite pointer type (Clause [[expr]]). Comparing pointers to members
|
| 29 |
+
is defined as follows:
|
| 30 |
+
|
| 31 |
+
- If two pointers to members are both the null member pointer value,
|
| 32 |
+
they compare equal.
|
| 33 |
+
- If only one of two pointers to members is the null member pointer
|
| 34 |
+
value, they compare unequal.
|
| 35 |
+
- If either is a pointer to a virtual member function, the result is
|
| 36 |
+
unspecified.
|
| 37 |
+
- If one refers to a member of class `C1` and the other refers to a
|
| 38 |
+
member of a different class `C2`, where neither is a base class of the
|
| 39 |
+
other, the result is unspecified.
|
| 40 |
+
``` cpp
|
| 41 |
+
struct A {};
|
| 42 |
+
struct B : A { int x; };
|
| 43 |
+
struct C : A { int x; };
|
| 44 |
+
|
| 45 |
+
int A::*bx = (int(A::*))&B::x;
|
| 46 |
+
int A::*cx = (int(A::*))&C::x;
|
| 47 |
+
|
| 48 |
+
bool b1 = (bx == cx); // unspecified
|
| 49 |
+
```
|
| 50 |
+
- Otherwise, two pointers to members compare equal if they would refer
|
| 51 |
+
to the same member of the same most derived object ([[intro.object]])
|
| 52 |
+
or the same subobject if indirection with a hypothetical object of the
|
| 53 |
+
associated class type were performed, otherwise they compare unequal.
|
| 54 |
``` cpp
|
| 55 |
struct B {
|
| 56 |
int f();
|
| 57 |
};
|
| 58 |
struct L : B { };
|
|
|
|
| 63 |
int (L::*pl)() = pb;
|
| 64 |
int (R::*pr)() = pb;
|
| 65 |
int (D::*pdl)() = pl;
|
| 66 |
int (D::*pdr)() = pr;
|
| 67 |
bool x = (pdl == pdr); // false
|
| 68 |
+
bool y = (pb == pl); // true
|
| 69 |
```
|
| 70 |
|
| 71 |
+
Two operands of type `std::nullptr_t` or one operand of type
|
| 72 |
+
`std::nullptr_t` and the other a null pointer constant compare equal.
|
| 73 |
|
| 74 |
+
If two operands compare equal, the result is `true` for the `==`
|
| 75 |
+
operator and `false` for the `!=` operator. If two operands compare
|
| 76 |
+
unequal, the result is `false` for the `==` operator and `true` for the
|
| 77 |
+
`!=` operator. Otherwise, the result of each of the operators is
|
| 78 |
+
unspecified.
|
| 79 |
+
|
| 80 |
+
If both operands are of arithmetic or enumeration type, the usual
|
| 81 |
+
arithmetic conversions are performed on both operands; each of the
|
| 82 |
+
operators shall yield `true` if the specified relationship is true and
|
| 83 |
+
`false` if it is false.
|
| 84 |
|