ホームページ ウェブフロントエンド jsチュートリアル JavaScript_js オブジェクト指向でクラスとオブジェクトを定義するいくつかの方法

JavaScript_js オブジェクト指向でクラスとオブジェクトを定義するいくつかの方法

May 16, 2016 pm 06:16 PM
クラスの定義 物体

この例を見てみましょう:

コードをコピーします コードは次のとおりです:

var a = 'グローバル' ;
(関数 () {
alert(a);
var a = 'ローカル';
})(); >
皆さん、まずはこの例を見て、出力は何だと思いますか? 'グローバル'?それとも「地元」?実際、そうではありません。出力は未定義です。これについて話したいだけです。
実際、JavaScript の動作メカニズムを見てみると、それは非常に簡単です。この現象は「ステートメント前」と考えることができます。しかし、もう少し深く掘り下げてみると、より明確に理解できるようになります。
これには実際にはオブジェクト プロパティ バインディング メカニズムが関係します。すべての JavaScript 関数はオブジェクトであるためです。関数内で宣言された変数は、このオブジェクトの「類似のプロパティ」と見なすことができます。オブジェクトのプロパティのバインディングは、言語では「アーリー バインディング」と「レイト バインディング」に分けられます。

[初期バインディング]
は、オブジェクトをインスタンス化する前にオブジェクトのプロパティとメソッドを定義することを指します。プログラムを解析するときに、事前にマシンコードに変換できます。 C や Java などの一般的な型付け言語はすべて、早期バインディング メカニズムを使用します。また、JavaScript は厳密に型指定された言語ではありません。 「遅延バインディング」メカニズムを使用します。
【Late Binding】
は、プログラムを実行する前にオブジェクトの種類を確認する必要はなく、オブジェクトがプロパティとメソッドをサポートしているかどうかだけを確認することを意味します。バインド前に、ペナルティなしでオブジェクトに対して多数の操作を実行できます。
上記のコードの「事前宣言」現象は、「遅延バインディング」メカニズムによって説明できます。関数のスコープ内では、すべての変数は「遅延バインド」されます。 つまり、ステートメントはトップレベルです。したがって、上記のコードは次のコードと一致しています:



コードをコピーします コードは次のとおりです: var a = 'グローバル';
(function () {
var a;
alert(a);
a = 'ローカル';
})(); >

alert(a) の前には、値を代入せずに a だけが宣言されていました。したがって、結果は想像できます。

RT: この記事で説明するのは、JavaScript でクラスとオブジェクトを定義するいくつかの方法です。 - ステートメント: 以下の内容のほとんどは「JavaScript Advanced Programming」から来ていますが、個人的な説明方法は異なります -- >
【直接量法】
オブジェクトを構築するために直接量を使用するのが最も基本的な方法です。しかし、デメリットもたくさんあります。




コードをコピーします
コードは次のとおりです。 var Obj = new Object; Obj.name = 'sun'; Obj.showName = function() { alert('this.name');
}


オブジェクト Obj を構築します。これには属性名とメソッド showName があります。しかし、別の同様のオブジェクトを構築したい場合はどうすればよいでしょうか?もう一度繰り返さなければなりませんか?
いいえ! 、特定の型のオブジェクトを返すファクトリ関数を使用して実装できます。工場と同じように、パイプラインは必要な特定の種類の結果を出力します。
【ファクトリメソッド】



コードをコピー

コードは次のとおりです。 function createObj (名前) { var tempObj = 新しいオブジェクト; tempObj.showName = 関数 () { alert(this.name); >return tempObj ;
}
var obj1 = createObj('obj_one');


多くの人はこれを使用しませんファクトリー関数 オブジェクトを構築する形式として。理由の 1 つはセマンティクスです。演算子 new を使用して構築するほど形式的ではありません。もう 1 つ大きな理由があります。このファクトリはオブジェクトを生成するたびに新しい関数 showName() を作成するためです。つまり、各オブジェクトのバージョンは異なりますが、実際には同じ関数を共有します。
ファクトリ関数の外で showName を定義し、属性を通じてメソッドを指す人もいます。これにより、この問題を回避できます。




コードをコピー

コードは次のとおりです。


function showName () {
alert(this.name); } function createObj(name) { var tempObj = 新しいオブジェクト ; tempObj.showName = showName; var obj1 = createObj('obj_one'); obj2 = createObj( 'obj_two');
残念ながら、このメソッドでは showName() 関数がオブジェクトのメソッドのように見えません。
[コンストラクターメソッド]
このメソッドは、上記のファクトリー関数の最初の問題、つまり新しい演算子が存在しない問題を解決するものです。しかし、それでも 2 番目の問題は解決できません。見てみましょう。
コードをコピーします コードは次のとおりです。

function Obj(name) {
this.name = 名前;
this.showName = function () {
alert(this.name);
}
var obj('obj_one'); 🎜>var obj2 = new Obj('obj_two');


利点は、new 演算子が自動的にオブジェクトを作成するため、コンストラクターで新しいオブジェクトを作成する必要がないことです。が実行され、これを介してのみこのオブジェクトにアクセスします。したがって、 this を通じてこのオブジェクトに直接値を割り当てることができます。また、これはデフォルトでコンストラクターの戻り値を指すため、return する必要はありません。
同時に、新しいキーワードを使用して必要なオブジェクトを作成すると、より「正式」に感じられます。
残念ながら、ファクトリ関数と同様にメソッド関数を繰り返し生成する問題はまだ解決できません。

[プロトタイプ手法]
この手法は、上記の手法と比較して、メソッド関数が複数回生成される問題を解決できるという大きな利点があります。オブジェクトのプロトタイプ プロパティを利用します。オブジェクト インスタンスをオーバーライドするにはプロトタイプに依存します。


var Obj = function () {}
Obj .prototype.name = 'me';
Obj.prototype.showName = function () {
alert(this.name);
var obj1 = new Obj();
var obj2 = new Obj();


プロトタイプに依存してコンストラクターを書き換えます。そのため、プロパティとメソッドは両方ともプロトタイプ参照を通じて与えられます。一度作成されました。残念ながら、この方法には 2 つの致命的な問題があります。
1.プロトタイプはコンストラクターのスコープ外にあるため、オブジェクトの構築時に必要なプロパティを記述する方法はありません。また、パラメーターを渡してオブジェクトを作成するときにプロパティ値を記述する方法はありません。値は、オブジェクトの作成後にのみオーバーライドできます。
2.致命的な問題は、プロパティがオブジェクトを指す場合、そのオブジェクトが複数のインスタンスで共有されることです。次のコードを考えてみましょう:



コードをコピー コードは次のとおりです: var Obj = function () { }
Obj.prototype.name = 'me';
Obj.prototype.flag = new Array('A', 'B');
Obj.prototype.showName = function () {
alert(this.name);
}
var obj1 = new Obj();
var obj2 = new Obj('C') ;
alert(obj1.flag); // A,B,C
alert(obj2.flag); //A,B,C


フラグ属性の場合object をポイントしている場合、obj1 と obj2 の両方のインスタンスがそれを共有します。obj1 の flag 属性のみを変更した場合でも、その変更はインスタンス obj2 に表示されます。
この問題に直面して、[コンストラクター メソッド] と [プロトタイプ メソッド] を組み合わせて補完する必要があるかどうかを考えなければなりません。 。 。
[コンストラクターとプロトタイプの混合メソッド]
コンストラクター メソッドを使用してプロパティを作成できるようにし、プロトタイプ メソッドを使用してメソッドを作成できます:




コードをコピー
コードは次のとおりです。 var Obj = function (name) { this.name = name; .flag = new Array(' A', 'B');
}
Obj.prototype = {
showName : function () {
alert(this.name);
}
var obj1 = new Obj();
var obj2 = new Obj();
obj1.flag.push('C'); // A,B,C
alert(obj2.flag); //A,B


このメソッドは、プロトタイプとコンストラクターの利点を効果的に組み合わせたもので、現在最も使用されているメソッドです。副作用が最も少ないです。
しかし、完璧を追求する人の中には、視覚的にまだ要件を満たしていないため、まだ満足していない人もいます。プロトタイプを介してメソッドを作成するプロセスは、依然として視覚的に人々にインスタンス メソッドのように見えないと感じさせるためです (特に、 )
したがって、プロトタイプをアクティブにし、それをコンストラクターに追加して、コンストラクターをより視覚的に統合することができます。この一連の処理は一度の判断だけで完了します。



コードをコピー


コードは次のとおりです:

var Obj = function (name) {
this.name = name;
this.flag = new Array('A', 'B'); _init == '未定義') {
Obj.prototype = {
showName : function () {
alert(this.name)
}
}; = true;
}
}


上記と同様に、_init をフラグとして使用して、プロトタイプに対してメソッドが作成されたかどうかを判断します。その場合、実行されません。実際、メソッドは依然としてプロトタイプを通じて作成されており、本質的には変わりません。唯一の違いは、このコンストラクターが「統一」されているように見えることです。
ただし、この動的プロトタイピング方法には問題があり、「JavaScript 高度なプログラミング」では詳しく説明されていません。最初のオブジェクトを作成するとき、オブジェクトがインスタンス化される前にプロトタイプが構築されないため、オブジェクトにはまったくアクセスできません。したがって、最初のオブジェクトはプロトタイプ メソッドにアクセスできません。同時に、この方法ではサブクラスの継承にも問題が発生します。
次の記事で解決策を説明します。

実際、使いやすさという点では、個人的にはこのように判断する必要はないと感じています。 。 。笑 ^_^
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。

ホットAIツール

Undresser.AI Undress

Undresser.AI Undress

リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover

AI Clothes Remover

写真から衣服を削除するオンライン AI ツール。

Undress AI Tool

Undress AI Tool

脱衣画像を無料で

Clothoff.io

Clothoff.io

AI衣類リムーバー

AI Hentai Generator

AI Hentai Generator

AIヘンタイを無料で生成します。

ホットツール

メモ帳++7.3.1

メモ帳++7.3.1

使いやすく無料のコードエディター

SublimeText3 中国語版

SublimeText3 中国語版

中国語版、とても使いやすい

ゼンドスタジオ 13.0.1

ゼンドスタジオ 13.0.1

強力な PHP 統合開発環境

ドリームウィーバー CS6

ドリームウィーバー CS6

ビジュアル Web 開発ツール

SublimeText3 Mac版

SublimeText3 Mac版

神レベルのコード編集ソフト(SublimeText3)

PHP の json_encode() 関数を使用して配列またはオブジェクトを JSON 文字列に変換する PHP の json_encode() 関数を使用して配列またはオブジェクトを JSON 文字列に変換する Nov 03, 2023 pm 03:30 PM

JSON (JavaScriptObjectNotation) は、Web アプリケーション間のデータ交換の一般的な形式となっている軽量のデータ交換形式です。 PHP の json_encode() 関数は、配列またはオブジェクトを JSON 文字列に変換できます。この記事では、PHPのjson_encode()関数の構文、パラメータ、戻り値、具体的な例などの使い方を紹介します。構文 json_encode() 関数の構文は次のとおりです。

ソースコードの探索: Python ではオブジェクトはどのように呼び出されますか? ソースコードの探索: Python ではオブジェクトはどのように呼び出されますか? May 11, 2023 am 11:46 AM

Wedge オブジェクトは主に 2 つの方法で作成されることがわかっています。1 つは Python/CAPI を使用する方法、もう 1 つは型オブジェクトを呼び出すことによる方法です。組み込み型のインスタンス オブジェクトについては、両方のメソッドがサポートされています。たとえば、リストは [] または list() を通じて作成できます。前者は Python/CAPI で、後者は呼び出し型オブジェクトです。ただし、カスタム クラスのオブジェクトの場合は、型オブジェクトを呼び出すことによってのみ作成できます。オブジェクトを呼び出すことができる場合、そのオブジェクトは呼び出し可能ですが、それ以外の場合は呼び出し可能ではありません。オブジェクトが呼び出し可能かどうかは、対応する型オブジェクトにメソッドが定義されているかどうかによって決まります。のように

PHP の Request オブジェクトとは何ですか? PHP の Request オブジェクトとは何ですか? Feb 27, 2024 pm 09:06 PM

PHP の Request オブジェクトは、クライアントからサーバーに送信される HTTP リクエストを処理するために使用されるオブジェクトです。 Request オブジェクトを通じて、リクエストを処理して応答するために、リクエスト メソッド、リクエスト ヘッダー情報、リクエスト パラメータなどのクライアントのリクエスト情報を取得できます。 PHP では、$_REQUEST、$_GET、$_POST などのグローバル変数を使用して、要求された情報を取得できますが、これらの変数はオブジェクトではなく配列です。リクエスト情報をより柔軟かつ便利に処理するために、次のことができます。

MySQLクエリ結果の配列をオブジェクトに変換するにはどうすればよいですか? MySQLクエリ結果の配列をオブジェクトに変換するにはどうすればよいですか? Apr 29, 2024 pm 01:09 PM

MySQL クエリ結果の配列をオブジェクトに変換する方法は次のとおりです。 空のオブジェクト配列を作成します。結果の配列をループし、行ごとに新しいオブジェクトを作成します。 foreach ループを使用して、各行のキーと値のペアを新しいオブジェクトの対応するプロパティに割り当てます。新しいオブジェクトをオブジェクト配列に追加します。データベース接続を閉じます。

Python の __contains__() 関数を使用してオブジェクトの包含操作を定義する Python の __contains__() 関数を使用してオブジェクトの包含操作を定義する Aug 22, 2023 pm 04:23 PM

Python の __contains__() 関数を使用して、オブジェクトの包含操作を定義します。Python は、さまざまな種類のデータを処理するための多くの強力な機能を提供する、簡潔で強力なプログラミング言語です。その 1 つは、__contains__() 関数を定義してオブジェクトの包含操作を実装することです。この記事では、__contains__() 関数を使用してオブジェクトの包含操作を定義する方法とサンプル コードを紹介します。 __contains__() 関数は Pytho です

Python の __le__() 関数を使用して、2 つのオブジェクトの小なり等しい比較を定義します。 Python の __le__() 関数を使用して、2 つのオブジェクトの小なり等しい比較を定義します。 Aug 21, 2023 pm 09:29 PM

タイトル: Python の __le__() 関数を使用して 2 つのオブジェクト以下の比較を定義する Python では、特別なメソッドを使用してオブジェクト間の比較演算を定義できます。その 1 つは __le__() 関数で、以下の比較を定義するために使用されます。 __le__() 関数は Python のマジック メソッドであり、「以下」演算を実装するために使用される特別な関数です。小なり等しい演算子 (<=) を使用して 2 つのオブジェクトを比較すると、Python

PHP における配列とオブジェクトの違いは何ですか? PHP における配列とオブジェクトの違いは何ですか? Apr 29, 2024 pm 02:39 PM

PHP では、配列は順序付けられたシーケンスであり、要素はインデックスによってアクセスされます。オブジェクトは、new キーワードによって作成されたプロパティとメソッドを持つエンティティです。配列へのアクセスはインデックス経由で、オブジェクトへのアクセスはプロパティ/メソッド経由で行われます。配列値が渡され、オブジェクト参照が渡されます。

C++ 関数がオブジェクトを返すときは何に注意する必要がありますか? C++ 関数がオブジェクトを返すときは何に注意する必要がありますか? Apr 19, 2024 pm 12:15 PM

C++ では、関数がオブジェクトを返すときに注意する点が 3 つあります。 オブジェクトのライフサイクルは、メモリ リークを防ぐために呼び出し元によって管理されます。ぶら下がりポインタを回避し、動的にメモリを割り当てるかオブジェクト自体を返すことにより、関数が戻った後もオブジェクトが有効なままであることを確認します。コンパイラーは、パフォーマンスを向上させるために、返されたオブジェクトのコピー生成を最適化する場合がありますが、オブジェクトが値セマンティクスによって渡される場合、コピー生成は必要ありません。

See all articles