Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Method overriding in c++ : is it compile time or run time polymorphism?

In C++, Is function overriding run time polymorphism or compile time polymorphism? I think it is compile time polymorphism because every information which is required to call the appropriate function is known to compiler early. As in the code below, obj.disp(); Here compiler knows obj is the object of base class so it will immediately resolve the call to disp() function of base class. and same for obj2.disp(); Here compiler knows obj2 is the object of derived class so it will call disp() function of derived class. I don't see why it is called run-time polymorphism.

Still in JAVA, people call function overriding as run time polymorphism. Please explain somebody....

#include <iostream>
using namespace std;

class A {
public:
  void disp(){
     cout<<"Super Class Function"<<endl;
  }
};

class B: public A{
public:
  void disp(){
     cout<<"Sub Class Function";
  }
};

int main() {
  //Parent class object
  A obj;
  obj.disp();
  //Child class object
  B obj2;
  obj2.disp();
  return 0;
}
like image 252
abhishek_7081 Avatar asked Dec 12 '25 03:12

abhishek_7081


1 Answers

Only virtual function calls are resolved at runtime. If the functions are non-virtual, as in your example, the calls are resolved at compile time.

Looking at the unoptimized assembly (generated by gcc 9.2 with -O0), the main function gets compiled to:

main:
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
        lea     rax, [rbp-1]
        mov     rdi, rax
        call    _ZN1A4dispEv
        lea     rax, [rbp-2]
        mov     rdi, rax
        call    _ZN1B4dispEv
        mov     eax, 0
        leave
        ret

The weird names _ZN1A4dispEv and _ZN1B4dispEv are the result of name mangling: in cases like this, the compiler creates unique names for functions (keep in mind that in assembly there is no oop). The actual mangling is compiler defined, but you can notice the name of the class (A and B, respectively) and the name of the function disp.

If disp were declared as virtual in A, then main would look like:

main:
        push    rbp
        mov     rbp, rsp
        sub     rsp, 16
->      mov     eax, OFFSET FLAT:vtable for A+16
->      mov     QWORD PTR [rbp-8], rax
        lea     rax, [rbp-8]
        mov     rdi, rax
        call    A::disp()
->      mov     eax, OFFSET FLAT:vtable for B+16
->      mov     QWORD PTR [rbp-16], rax
        lea     rax, [rbp-16]
        mov     rdi, rax
        call    B::disp()
        mov     eax, 0
        leave
        ret

The lines marked with -> are vtable queries, used to resolve the function call at runtime.

like image 101
Paul92 Avatar answered Dec 13 '25 22:12

Paul92



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!