开发者

Multiple dispatch and multi-methods

开发者 https://www.devze.com 2023-01-28 19:41 出处:网络
What are they, what\'s the different between them? Many sources, l开发者_StackOverflowike Wikipedia, claim they\'re the same thing, but others explicitly say the opposite, like sbi in this question:

What are they, what's the different between them?

Many sources, l开发者_StackOverflowike Wikipedia, claim they're the same thing, but others explicitly say the opposite, like sbi in this question:

First: "Visitor Pattern is a way to simulate Double Dispatching in C++." This is, erm, not fully right. Actually, double dispatch is one form of multiple dispatch, which is a way to simulate (the missing) multi-methods in C++.


They are the same.

When you call a virtual method in C++, the actual method to run is based on the runtime type of the object them method is invoked on. This is called "single dispatch" because it depends on the type of a single argument (in this case, the implicit 'this' argument). So, for example, the following:

class Base {
  public:
    virtual int Foo() { return 3; }
}

class Derived : public Base {
  public:
    virtual int Foo() { return 123; }
}

int main(int argc, char *argv[]) {
  Base* base = new Derived;
  cout << "The result is " << base->Foo();
  delete base;
  return 0;
}

When run, the above program prints 123, not 3. So far so good.

Multiple-dispatch is the ability of a language or runtime to dispatch on both the type of the 'this' pointer and the type of the arguments to the method. Consider (sticking with C++ syntax for the moment):

class Derived;

class Base {
  public:
    virtual int Foo(Base *b) { cout << "Called Base::Foo with a Base*"; }
    virtual int Foo(Derived *d) { cout << "Called Base::Foo with a Derived*"; }
}

class Derived : public Base {
  public:
    virtual int Foo(Base *b) { cout << "Called Derived::Foo with a Base*"; }
    virtual int Foo(Derived *d) { cout << "Called Derived::Foo with a Derived*"; }
}

int main(int argc, char *argv[]) {
  Base* base = new Derived;
  Base* arg = new Derived;

  base->Foo(arg);

  delete base;
  delete arg;
  return 0;
}

If C++ had multiple-dispatch, the program would print out "Called Derived::Foo with a Dervied*". (Sadly, C++ does not have multiple-dispatch, and so the program prints out "Called Derived::Foo with a Base*".)

Double-dispatch is a special case of multiple-dispatch, often easier to emulate, but not terribly common as a language feature. Most languages do either single-dispatch or multiple-dispatch.

0

精彩评论

暂无评论...
验证码 换一张
取 消