JavaScript はプロトタイプ指向の言語です。
コンストラクター関数から実際のオブジェクトを構築でき、オブジェクトが持つことができるほぼすべての機能を備えています。
- コンストラクタ。
- メソッド (つまり、JavaScript の関数)。
- プロパティ (ECMA-Script 5 以降、「ゲッター/セッター」)。
- インスタンス。
JavaScript では、関数を含むすべてのオブジェクトにプロトタイプがあります。プロトタイプ自体は、オブジェクト全体の新しく作成されたインスタンスにオブジェクト メンバーを追加する基本的な方法です。
var constructor = function() { };
constructor.prototype.text = "hello world";
alert(new constructor().text); // This alerts hello world
JavaScript がオブジェクト指向プログラミング(スクリプト) 言語ではないのはなぜですか? オブジェクト指向プログラミングの定義の要件に適合する機能がないためです。
- ポリモーフィズム:いいえ。プロトタイプ メンバーの動作を変更することはできますが、これは識別子を再利用しているだけです。疑似派生オブジェクトのメンバーの以前の実装にアクセスすることはできません。
- 継承:まったくありません。プロトタイプ チェーンは継承に匹敵するかもしれませんが、JavaScript (ECMA-Script 5.x 以前のバージョン) には、他の OOP ベースの言語 (Java、C#、Ruby、Python、VisualBasic.NET など) のような構文ベースの継承はありません。 )。
- カプセル化。はい、もちろんですが、実際のプライベートまたは内部オブジェクト メンバーを作成する方法はありません。
他の詳細について言及するのを忘れていたのかもしれませんが、正直なところ、これは良い要約だと思います。
アップデートとまとめ
主な違いは、オブジェクト指向プログラミング言語には、オブジェクト指向プログラミング言語と見なされるためにオブジェクト指向パラダイムが持たなければならない機能があることです。したがって、JavaScript は実際のポリモーフィズムと継承を欠いているため、現時点では実際のオブジェクト指向プログラミング言語ではありません。
更新: ES2015 以降では状況は変わりましたか?
審美的に言えば、はい、ES2015 以降では、完全ではありませんが、よりオブジェクト指向プログラミングに近いものを考慮することができる大きな改善があります:スーパークラスを呼び出すための構文糖衣。
例えば:
class A {
doStuff() {
console.log("hello world");
}
}
class B extends A {
doStuff() {
super.doStuff();
console.log("...and goodbye!");
}
}
これがポリモーフィズムです。より特殊化されたクラスは、その基本クラスをオーバーライドして、関数の動作を完全に変更するか、基本クラスが既に行っていたことを実行して、関数に新しいコードを追加できます。
ところで、ES2015以降にはまだ真のカプセル化が欠けています:アクセス修飾子はどこですか? private
public
どこにも。
そして、結局のところ、ES2015 以降ではクラスベースの OOP が実装されていますが、それでも ECMAScript 5.x の上にある構文糖衣レイヤーです。上記のコードは、フードの下のプロトタイプでも機能し、同じように機能します。あたかも ECMAScript 5.x でコーディングするかのように:
function A() {
}
A.prototype.doStuff = function() {
console.log("hello world");
};
function B() {
}
B.prototype = Object.create(A.prototype);
B.prototype.doStuff = function() {
A.prototype.doStuff.call(this);
console.log("...and goodbye!");
};
ES2020 は既にアクセス修飾子を提案しており、JavaScript をオブジェクト指向プログラミングを完全にサポートする別の言語と見なすことができるため、この回答を再度更新する必要があることを願っています!