【问题标题】:C++ Why the operator-> breaks the nested operator() call?C++ 为什么 operator-> 会破坏嵌套的 operator() 调用?
【发布时间】:2017-12-16 07:22:10
【问题描述】:

当我在指向具有重载操作符()(又名函子)的类的指针上使用解引用运算符时 - 它就像一个魅力:

struct Functor {
    int operator()(int a, float b) {
        return a+b;
    }
};

Functor g;
Functor * f = &g;
g(1,2.);
(*f)(1,.2);
f->operator()(1,2.f);

但形式

// f->(1,2.f); // doesn't compile (expected unqualified-id)

为什么会这样?

【问题讨论】:

  • f->() 在 C++(或 C)中的语法无效,无论好坏。你是在问为什么语言设计者选择不允许它?
  • @JohnZwinck 但是为什么语法不正确?我希望 -> 是 (*ptr) 的快捷方式,所以如果我们可以在取消引用和优先级括号之后应用 (*ptr)() - 为什么我们不能将 () 应用到 ->跨度>
  • f->*f. 的“别名”,不是你想的那样。
  • @Slava 哦,我明白了.. 现在因为点 '.' 才有意义
  • @barney .*one 运算符——“指向成员的指针解引用运算符”。有指针时对应的运算符是->*。正确的语法是(pvar->*p1)(1,2)(或((*pvar).*p1)(1,2))。

标签: c++ operator-overloading operators


【解决方案1】:

在 C++ 中,点 (.) 运算符用于访问成员并调用对象上的方法。在您的示例中,您可以通过以下方式使用:

g.operator()(1, 2.);

它会编译得很好。相反,您以 equivalent(更常规的)表示法调用运算符,如下所示:

g(1,2.);

很干净。您要做的是实现相同的干净运算符调用,但从指针使用-> 表示法,认为同样的魔法将适用。可悲的是,它不是那样工作的。在 C++ 中,p->a()(*p).a() 的简写。换句话说,这是一种

  1. 取消引用指针 -- *p;
  2. 取消引用的对象调用方法(或访问成员) -- (*p).a();

取消引用的对象不再是指针(*p 周围的括号实现了这一点),这就是可以调用点运算符的原因。所以当你写的时候:

f->(1,2.f);

你写的是这样的:

(*f).(1, 2.f);

这不是有效的 C++,因为(*f) 不代表Functor 对象的地址。请注意:

f->operator()(1,2.f);

是有效的,因为它意味着:

(*f).operator()(1, 2.f);

有效。相当于我上面写的第一行:g.operator()(1, 2.);

希望这会有所帮助。

【讨论】:

    猜你喜欢
    • 2018-06-15
    • 2013-02-18
    • 2020-09-20
    • 1970-01-01
    • 1970-01-01
    • 2012-01-05
    相关资源
    最近更新 更多