前に書く
このシリーズの記事は、「JavaScript Design Patterns」という本の研究に基づいています。最初は、本を読むだけで、追加のメモをとる必要はないと感じましたが、後で、本の内容の一部が理解できないことに気付きました。簡単ではないので、本の説明に基づいて理解を整理して記録しました。一緒に学んでいきたいと思います。記事に間違っていることがあれば、批判して訂正してください。みんなで一緒に進歩できますよ〜
この記事から、JavaScriptの設計パターンを実際に学び始めます。まず、最初の設計パターンであるシングルトンパターンを学びます。
シングルトンモードの意味
シングルトンパターンは、実際にはJSで最も単純で最も一般的な設計パターンであり、その意味は比較的単純です。つまり、クラスにインスタンスが1つしかないことを確認し、それにアクセスするためのグローバルアクセスポイントのみを提供します。この文が理解しにくい場合は、もう1つ栗をあげましょう。CDNを使用してプロジェクトコードにJSライブラリファイルを導入します。実際、その入り口はjQueryなどのシングルトンです。ページの<script>タグを使用してjQueryを紹介すると、JSコードの「$」記号を使用してjQueryのすべてのメソッドにアクセスできます。ここでの$記号は、実際にはjQueryが外部に提供する唯一のアクセスポイントであり、jQueryでもあります。オブジェクトの唯一のインスタンス、私たちはそれを理解することができます。
シングルトンモードのアプリケーションシナリオ
シングルトンモードには、実際には多くのアプリケーションシナリオがあります。たとえば、一部のオブジェクトに1つのオブジェクトのみが必要な場合は、スレッドプール、グローバルキャッシュ、ブラウザウィンドウオブジェクトなどのシングルトンモードを使用できます。また、フロントエンドとバックエンドを操作する場合も使用できます。シングルトンはデータベース接続、webSocket接続などに使用でき、一部のフロントエンドUIコンポーネントは、ポップアップウィンドウなどのシングルトンも使用できます。最も簡単なのは、ポップアップウィンドウにログインすることです。ユーザーがログインしている場合、ログインポップアップウィンドウは表示されません。ユーザーがログインしていない場合、ユーザーがログインボタンをクリックした後にポップアップウィンドウが表示されます。ポップアップウィンドウが表示されている場合、ユーザーがログインボタンをクリックするたびにポップアップウィンドウを作成することはできません。最初にポップアップウィンドウを作成し、ユーザーがボタンをクリックしたときにのみ表示できるので、ログインボタンをクリックするたびに表示するのではなく、アプリケーション全体でログインポップアップウィンドウが1つだけになるようにすることができます。彼は複数のポップアップウィンドウを作成し、不要なDOMの浪費を引き起こしました。
シングルトンモード実現のアイデア
上記のアプリケーションシナリオで説明したように、ボタンをクリックするたびにポップアップウィンドウを表示するかどうかを制御するだけでよく、毎回新しいポップアップウィンドウを作成する必要はありません。このような要件を実現する方法は、実際には非常に簡単です。変数を定義するだけで済みます。この変数は、ポップアップウィンドウが作成されたか、シングルトンが作成されたかを示すために使用されます。作成された場合、作成されたオブジェクトを返します。作成されていない場合は、新しいオブジェクトを作成するだけです。したがって、シングルトンパターンの実現は、1つの変数のみで完了できます。
シングルトンモードの特定の実装
1.通常の実現
JS自体は「クラス」のないプログラミング言語であるため、ここでは従来の言語でのシングルトンパターンの実装プロセスについては説明しません。クラスの概念はES6の初めに追加されましたが、構文上の砂糖に近いものです。したがって、JSでのシングルトンパターンの実装は、従来のプログラミング言語での実装プロセスと一貫性がなく、従来の言語でのシングルトンパターンの実装プロセスをJSにコピーする必要はありません。JSではシングルトンモードの方が実装しやすいと言えます。
シングルトンモードのコアコンセプトは、実際には2つのポイントのみです。つまり、オブジェクトが1つだけであることを確認し、グローバルアクセスを提供します。
次に、JSでは、オブジェクトリテラルメソッドを使用して作成したオブジェクトは、「1つのオブジェクトのみ」の条件を保証できます。次に、「グローバルアクセスの提供」の条件を満たすように、このオブジェクトをグローバルスコープで定義します。したがって、組み合わせて、オブジェクトリテラルを介して、グローバルスコープで定義されたオブジェクトは、シングルトンモードの2つの条件を完全に満たします。したがって、JSでシングルトンモードを実装する最も簡単な方法は次のとおりです。
var objectA = {}; //定义在全局作用域中
ただし、上記の方法はシングルトンモードを実装していますが、問題があります。グローバルスコープでオブジェクトを定義すると、スコープ内で環境汚染が発生し、コードの後半でこのオブジェクトが誤って変更される可能性があります。ハプニング。これらの2つの問題は、次の2つの方法で解決します。
1.名前空間を使用する
名前付けの使用は、実際にはグローバルスコープの汚染の問題を解決しませんが、次のように、ある程度、グローバルスコープ内の変数の数を減らすことができます。
var nameSpaceA = {
objectA: function() {
},
objectB: function() {
}
};
上記のコードでは、objectAとobjectBをnameSpaceAの属性として直接定義します。これにより、グローバルスコープ内の変数の数が減り、変数がグローバルスコープと直接対話する機会がある程度回避されます。
2.クロージャーを使用してプライベート変数をカプセル化します
名前付けアプローチに加えて、次のように、クロージャーを使用して、一部の変数をプライベート変数として直接カプセル化できます。
var objectB = (function() {
var _name = 'www.xbeichen.cn';
var _age = 25;
return {
getInfo: function() {
return `${_name}的年龄已经是${_age}岁了哦`;
}
}
})();
上記のコードでは、2つの変数_nameと_ageをクロージャーでカプセル化して、これら2つの変数にグローバルスコープでアクセスできないようにします。
2つの不活性シングルトン
レイジーシングルトンはシングルトンパターンの重要なポイントであり、その意味は非常に単純です。最初ではなく、必要に応じてオブジェクトを作成します。
例としてログインウィンドウを使用しましょう。レイジーシングルトンを使用しない場合は、次のように実装できます。システムに入ると、このログインポップアップも作成されますが、現時点では非表示になっています。ユーザーがログインボタンをクリックすると、その表示プロパティが変更され、ユーザーがログインするためのログインパネルがポップアップ表示されます。しかし、これに関する1つの問題は、ユーザーがWebページ上の他の情報を表示するためだけにWebページを開いたが、ログインしたくない場合、ログインポップアップウィンドウを作成するだけで、使用されないため、DOMが発生することです。廃棄物。
レイジーシングルトンを使用している場合は、システムに入ると、最初はログインポップアップウィンドウが作成されず、ユーザーがログインボタンをクリックしたときにのみ作成されて表示されます。 、このようにして、冗長なDOMの浪費が回避されます。ただし、これには問題があります。クリックするたびにこのポップアップウィンドウが作成されるため、これは遅延の特性を実現するだけで、シングルトンの効果はありません。この問題は実際には非常に簡単に解決できます。マークする変数を定義します。ポップアップウィンドウを作成するかどうかは問題ないため、次のように、レイジーシングルトンの効果が得られます。
//惰性单例
var createLoginView = (function() {
var div;
return function() {
if(!div) {
div = document.createElement('div');
div.innerHTML = '登录弹窗';
div.style.display = 'none';
document.body.appendChild(div);
}
return div;
}
})();
document.getElementById('loginButton').onclick = function() {
var loginView = createLoginView();
loginView.style.display = 'block';
}
上記のコードでは、遅延シングルトンを実装しましたが、このコードは単一責任の原則に違反しています。すべてのロジックはcreateLoginViewオブジェクト内にあります。後でiframeタグとスクリプトタグを作成する場合は、createLoginView内のコードを変更する必要があります。もう一度コピーする必要があります。これは非常に悪いことです。
一般的なレイジーシングルトンは、次の方法で実装します。
//通用的惰性单例
var getSingle = function(fn) {
var result;
return function() {
return result || (result = fn.apply(this,arguments));
}
};
var createLoginView = function() { //创建div
var div = document.createElement('div');
div.innerHTML = '登录弹窗';
div.style.display = 'none';
document.body.appendChild(div);
return div;
};
var createSingleLoginView = getSingle(createLoginView);
var createIframeView = function() { //创建iframe
var iframe = document.createElement('iframe');
document.body.appendChild(iframe);
return iframe;
};
var createSingleIframeView = getSingle(createIframeView);
document.getElementById('loginButton').onclick = function() {
var loginView = createSingleLoginView();
loginView.style.display = 'block';
}
document.getElementById('iframeButton').onclick = function() {
var iframeView = createSingleIframeView();
iframeView.src = 'http://www.xbeichen.cn';
}
上記のコードでは、ラベルオブジェクトを作成するコードとシングルトンを管理するコードを異なる方法で配置しています。これら2つの方法は相互に影響を与えませんが、組み合わせて使用すると、シングルトンモードの実現が完了します。これは間違いなく非常に成功しています。
総括する
この記事では、JSでの最も単純なシングルトンパターンの実装を紹介します。導入時には、従来の言語のように機械的にコピーするのではなく、レイジーシングルトンの実装を含め、JS言語の特性を最大限に活用して実装しました。この例では、JSの高次関数とクロージャのナレッジポイントが使用されているため、設計パターンを学習する前に、JSの特定の高度な基本知識が必要です。