What is the difference between dynamic dispatch and late binding in C++?

后端 未结 11 1517
臣服心动
臣服心动 2020-12-07 10:52

I\'ve recently read about the Dynamic Dispatch on Wikipedia and couldn\'t understand the difference between dynamic dispatch and late binding in C++.

When each one

相关标签:
11条回答
  • 2020-12-07 11:30

    In C++, both are same.

    In C++, there are two kinds of binding:

    • static binding — which is done at compile-time.
    • dynamic binding — which is done at runtime.

    Dynamic binding, since it is done at runtime, is also referred to as late binding and static binding is sometime referred to as early binding.

    Using dynamic-binding, C++ supports runtime-polymorphism through virtual functions (or function pointers), and using static-binding, all other functions calls are resolved.

    0 讨论(0)
  • 2020-12-07 11:36

    In C++, both dynamic dispatch and late binding is the same. Basically, the value of a single object determines the piece of code invoked at runtime. In languages like C++ and java dynamic dispatch is more specifically dynamic single dispatch which works as mentioned above. In this case, since the binding occurs at runtime, it is also called late binding. Languages like smalltalk allow dynamic multiple dispatch in which the runtime method is chosen at runtime based on the identities or values of more than one object.

    In C++ we dont really have late binding, because the type information is known. Thus in the C++ or Java context, dynamic dispatch and late binding are the same. Actual/fully late binding, I think is in languages like python which is a method-based lookup rather than type based.

    0 讨论(0)
  • 2020-12-07 11:37

    I suppose the meaning is when you have two classes B,C inherits the same father class A. so, pointer of the father (type A) can hold each of sons types. The compiler cannot know what the type holds in the pointer in certain time, because it can change during the program run.

    There is special functions to determine what the type of certain object in certain time. like instanceof in java, or by if(typeid(b) == typeid(A))... in c++.

    0 讨论(0)
  • 2020-12-07 11:38

    Late binding is calling a method by name during runtime. You don't really have this in c++, except for importing methods from a DLL.
    An example for that would be: GetProcAddress()

    With dynamic dispatch, the compiler has enough information to call the right implementation of the method. This is usually done by creating a virtual table.

    0 讨论(0)
  • 2020-12-07 11:38

    This question might help you.

    Dynamic dispatch generally refers to multiple dispatch.

    Consider the below example. I hope it might help you.

        class Base2;
        class Derived2; //Derived2 class is child of Base2
    class Base1 {
        public:
            virtual void function1 (Base2 *);
            virtual void function1 (Derived2 *);
    }
    
    class Derived1: public Base1 {
        public:
        //override.
        virtual void function1(Base2 *);
        virtual void function1(Derived2 *);
    };
    

    Consider the case of below.

    Derived1 * d = new Derived1;
    Base2 * b = new Derived2;
    
    //Now which function1 will be called.
    d->function1(b);
    

    It will call function1 taking Base2* not Derived2*. This is due to lack of dynamic multiple dispatch.

    Late binding is one of the mechanism to implement dynamic single dispatch.

    0 讨论(0)
  • 2020-12-07 11:40

    Let me give you an example of the differences because they are NOT the same. Yes, dynamic dispatch lets you choose the correct method when you are referring to an object by a superclass, but that magic is very specific to that class hierarchy, and you have to do some declarations in the base class to make it work (abstract methods fill out the vtables since the index of the method in the table cant change between specific types). So, you can call methods in Tabby and Lion and Tiger all by a generic Cat pointer and even have arrays of Cats filled with Lions and Tigers and Tabbys. It knows what indexes those methods refer to in the object's vtable at compile-time (static/early binding), even though the method is selected at run-time (dynamic dispatch).

    Now, lets implement an array that contains Lions and Tigers and Bears! ((Oh My!)). Assuming we don't have a base class called Animal, in C++, you are going to have significant work to do to because the compiler isn't going to let you do any dynamic dispatch without a common base class. The indexes for the vtables need to match up, and that can't be done between unreleated classes. You'd need to have a vtable big enough to hold the virtual methods of all classes in the system. C++ programmers rarely see this as a limitation because you have been trained to think a certain way about class design. I'm not saying its better or worse.

    With late binding, the run-time takes care of this without a common base class. There is normally a hash table system used to find methods in the classes with a cache system used in the dispatcher. Where in C++, the compiler knows all the types. In a late-bound language, the objects themselves know their type (its not typeless, the objects themselves know exactly who they are in most cases). This means I can have arrays of multiple types of objects if I want (Lions and Tigers and Bears). And you can implement message forwarding and prototyping (allows behaviors to be changed per object without changing the class) and all sorts of other things in ways that are much more flexible and lead to less code overhead than in languages that don't support late binding.

    Ever program in Android and use findViewById()? You almost always end up casting the result to get the right type, and casting is basically lying to the compiler and giving up all the static type-checking goodness that is supposed to make static languages superior. Of course, you could instead have findTextViewById(), findEditTextById(), and a million others so that your return types match, but that is throwing polymorphism out the window; arguably the whole basis of OOP. A late-bound language would probably let you simply index by an ID, and treat it like a hash table and not care what the type was being indexed nor returned.

    Here's another example. Let's say that you have your Lion class and its default behavior is to eat you when you see it. In C++, if you wanted to have a single "trained" lion, you need to make a new subclass. Prototyping would let you simply change the one or two methods of that particular Lion that need to be changed. It's class and type don't change. C++ can't do that. This is important since when you have a new "AfricanSpottedLion" that inherits from Lion, you can train it too. The prototyping doesn't change the class structure so it can be expanded. This is normally how these languages handle issues that normally require multiple inheritance, or perhaps multiple inheritance is how you handle a lack of prototyping.

    FYI, Objective-C is C with SmallTalk's message passing added and SmallTalk is the original OOP, and both are late bound with all the features above and more. Late bound languages may be slightly slower from a micro-level standpoint, but can often allow the code to structured in a way that is more efficient at a macro-level, and it all boils down to preference.

    0 讨论(0)
提交回复
热议问题