ベストアンサー
実際、Cにはポリモーフィズムの概念はありません。ポリモーフィズムはオブジェクト指向プログラミングのプロパティです。 CはOOPではないため、Cにはポリモーフィズムの概念がありません。 C ++は、オブジェクト指向プログラミング言語であるため(完全ではありません)、持っています。
ポリモーフィズムとは、多くの形式を持つことを意味します。 C ++には主に2つのタイプのポリモーフィズムがあります。
- コンパイル時ポリモーフィズム
- ランタイムポリモーフィズム
- コンパイル時のポリモーフィズム:このタイプのポリモーフィズムは、関数のオーバーロードまたは演算子のオーバーロードによって実現されます。
- 関数のオーバーロード:同じ名前でパラメータが異なる複数の関数がある場合、これらの関数はオーバーロードされていると言われます。関数は、引数の数の変更または引数のタイプの変更によってオーバーロードされる可能性があります。 。
#include
using namespace std;
class Geeks
{
public:
// function with 1 int parameter
void func(int x)
{
cout << "value of x is " << x << endl;
}
// function with same name but 1 double parameter
void func(double x)
{
cout << "value of x is " << x << endl;
}
// function with same name and 2 int parameters
void func(int x, int y)
{
cout << "value of x and y is " << x << ", " << y << endl;
}
};
int main() {
Geeks obj1;
// The first "func" is called
obj1.func(7);
// The second "func" is called
obj1.func(9.132);
// The third "func" is called
obj1.func(85,64);
return 0;
}
- 演算子のオーバーロード: C ++には演算子をオーバーロードするオプションもあります。たとえば、文字列クラスの演算子( ‘+’)を作成して、2つの文字列を連結できます。これは、オペランドに加算するタスクを持つ加算演算子であることがわかっています。したがって、整数オペランドの間に配置された単一の演算子「+」はそれらを追加し、文字列オペランドの間に配置された場合はそれらを連結します。
#include
using namespace std;
class Complex {
private:
int real, imag;
public:
Complex(int r = 0, int i =0) {real = r; imag = i;}
// This is automatically called when "+" is used with
// between two Complex objects
Complex operator + (Complex const &obj) {
Complex res;
res.real = real + obj.real;
res.imag = imag + obj.imag;
return res;
}
void print() { cout << real << " + i" << imag << endl; }
};
int main()
{
Complex c1(10, 5), c2(2, 4);
Complex c3 = c1 + c2; // An example call to "operator+"
c3.print();
}
2。 ランタイムポリモーフィズム::このタイプのポリモーフィズムは、関数のオーバーライドによって実現されます。
- 関数のオーバーライド:一方、派生クラスに基本クラスのメンバー関数の1つに対する定義がある場合に発生します。その基本機能はオーバーライドされると言われています。
#include
using namespace std;
// Base class
class Parent
{
public:
void print()
{
cout << "The Parent print function was called" << endl;
}
};
// Derived class
class Child : public Parent
{
public:
// definition of a member function already present in Parent
void print()
{
cout << "The child print function was called" << endl;
}
};
//main function
int main()
{
//object of parent class
Parent obj1;
//object of child class
Child obj2 = Child();
// obj1 will call the print function in Parent
obj1.print();
// obj2 will override the print function in Parent
// and call the print function in Child
obj2.print();
return 0;
}
回答
これが多態性の定義であるため、コードは実行時まで、オブジェクトの実際のクラスが何であるかを知っています。
従来の例を使用して、draw()メソッドを持つ基本クラスShapeについて考えてみましょう。 Shapeには2つのサブクラスがあります。CircleとSquareは、どちらもdraw()をオーバーライドして、それぞれ円と正方形を描画します。
これで、アプリケーションでユーザーが複数の形状を作成できるようになりました。そして、ビュー更新関数はそれらを繰り返して呼び出します。
currentShape.draw()
コンパイラは、コンパイル時にcurrentShapeが正方形か円かを知る方法がありません。したがって、どのdraw()実装を呼び出すか。決定は実行時に行う必要があります。
確かに、コンパイラがオブジェクトの実際のクラスを推測できる場合があります。その場合、ランタイムルックアップが最適化される可能性があります。
ポリモーフィズムとこのランタイムは、関数の1つ(または複数)の実際のデータ型に応じて、関数の正しい実装にディスパッチされることに注意してください。引数は非常に便利で強力です。