简体   繁体   English

为什么调用箭头( - >)运算符失败?

[英]Why does this call to arrow (->) operator fail?

Consider the following code : 请考虑以下代码:

#include <iostream>

class Test
{
public:
    Test() : a{ 0 }
    {}

    void print() const
    {
        std::cout << "a : " << a << std::endl;
    }

    void operator->()
    {
        a = 5;
    }

    void operator++()
    {
        ++a;
    }

public:
    int a;
};

int main()
{
    Test a;
    a.print();

    // Increment operator
    a.operator++();      // CORRECT
    ++a;                 // CORRECT
    a.print();

    // Indirection operator
    a.operator->();      // CORRECT
    a->;                 // INCORRECT
    a.print();
}

Why is the call to the second -> operator incorrect? 为什么第二个->运算符的调用不正确? I know this usage of -> is different from the general usage, but is such usage disallowed by the standard? 我知道这种用法->与一般用法不同,但是这种用法是否被标准禁止?

The sub-section on Class member access from Overloaded Operators from CPP standard draft (N4713) states this: 来自CPP标准草案(N4713)的重载运营商的 类成员访问的子部分声明:

16.5 Overloaded operators 16.5重载运算符
... ...
16.5.6 Class member access [over.ref] 16.5.6类成员访问[over.ref]
1. operator-> shall be a non-static member function taking no parameters. 1. operator->是一个不带参数的非静态成员函数。 It implements the class member access syntax that uses -> . 它实现了使用->的类成员访问语法。

 postfix-expression -> template(opt) id-expression //This!! postfix-expression -> pseudo-destructor-name 

An expression x->m is interpreted as (x.operator->())->m for a class object x of type T if T::operator->() exists and if the operator is selected as the best match function by the overload resolution mechanism (16.3). 如果存在T::operator->()并且如果选择运算符作为最佳匹配函数,则表达式x->m被解释为(x.operator->())->m用于类型为T的类对象x通过重载解析机制(16.3)。

As you can see the id-expression is very much needed if the -> operator is overloaded. 正如您所看到的,如果->运算符被重载,则非常需要id-expression

Class member access [expr.ref/1] §7.6.1.5/1 : 类成员访问[expr.ref / 1]§7.6.1.5/ 1

  1. A postfix expression followed by a dot . 后缀表达式后跟一个点. or an arrow -> , optionally followed by the keyword template ([temp.names]), and then followed by an id-expression , is a postfix expression. 或箭头-> ,可选地后跟关键字模板 ([temp.names]), 然后是id-expression ,是后缀表达式。 The postfix expression before the dot or arrow is evaluated; 评估点或箭头之前的后缀表达式 ; the result of that evaluation, together with the id-expression , determines the result of the entire postfix expression . 该评估的结果id-expression一起确定整个后缀表达式的结果

Names [expr.prim.id] (§7.5.4) : 名称[expr.prim.id](§7.5.4)

id-expression: ID-表达:
unqualified-id 不合格-ID
qualified-id 合格-ID

  1. An id-expression is a restricted form of a primary-expression. id表达式是primary-expression的限制形式。 [ Note: An id-expression can appear after . [注意:后面会出现一个id表达式。 and -> operators. 和 - >运算符。 — end note ] - 结束说明]

  2. An id-expression that denotes a non-static data member or non-static member function of a class can only be used: 只能使用表示非静态数据成员或类的非静态成员函数的id表达式:

    2.1. 2.1。 as part of a class member access in which the object expression refers to the member's class or a class derived from that class, or 作为类成员访问的一部分,其中对象表达式引用成员的类或从该类派生的类,或
    2.2. 2.2。 to form a pointer to member ([expr.unary.op]), or 形成指向成员的指针([expr.unary.op]),或
    2.3. 2.3。 if that id-expression denotes a non-static data member and it appears in an unevaluated operand. 如果该id-expression表示非静态数据成员,则它出现在未评估的操作数中。

As said by MM, a->; 如MM所说, a->; is a sintax error . 是一个sintax错误 A non-static member operator function without argument is a prefix (as operator++() ; postfix is operator++(int)) a.operator->(); 参数的非静态成员运算符函数是前缀(作为operator++() ;后缀是operator++(int)) a.operator->(); would be ->a; 会是->a; (wow!), but this is again a sintax error. (哇!),但这是一个sintax错误。 The standard specifies the fine details... 该标准规定了细节......

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

相关问题 为什么g ++在带有转换运算符和不可访问的函数调用运算符的类型中失败了std :: function &lt;&gt;的init? - Why does g++ fail init of std::function<> from type with conversion operator and inaccessible function call operators? 为什么我对operator *的使用失败? - Why does my use of operator* fail? 为什么使用此全局`operator &lt;&lt;`无法编译? - Why does using this global `operator<<` fail to compile? 为什么mkdir()后跟ofstream :: operator &lt;&lt;失败,但权限被拒绝? - Why does mkdir() followed by ofstream::operator<< fail with permission denied? 为什么删除操作符会在调试模式下导致调试断言失败? - Why does delete operator causes Debug Assertion Fail in Debug Mode? 为什么在函数参数中使用赋值运算符会失败? - Why does this use of assignment operator in a function argument fail? 为什么sizeof运算符无法在函数模板中工作? - Why does sizeof operator fail to work inside function template? 为什么这个程序调用operator()而不是构造函数? - Why does this program call operator () instead of the constructor? 为什么 std::tuple 调用运算符 &lt;=&gt; 两次? - Why does std::tuple call operator <=> twice? 为什么赋值运算符调用构造函数? - Why does assignment operator call constructor?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM