ホームページ ウェブフロントエンド jsチュートリアル JavaScriptのデザインパターン(カプセル化)_JavaScriptスキルを学ぶ

JavaScriptのデザインパターン(カプセル化)_JavaScriptスキルを学ぶ

May 16, 2016 pm 03:29 PM
javascript カプセル化 デザインパターン

JavaScript では、抽象クラスとインターフェイスはサポートされていません。 JavaScript 自体も弱い型付け言語です。 JavaScript には、型をカプセル化する機能がありませんし、それ以上のことを行う必要もありません。 JavaScript でデザインパターンを実装する場合、型を区別しないことは不名誉とも言えますし、救いとも言えます。

デザインパターンの観点から見ると、パッケージングは​​より重要なレベルでパッケージングの変更に反映されます。

変更をカプセル化することにより、システムの進化中に、システムの安定した部分と変更されやすい部分が分離されます。これらの部分がカプセル化されている場合は、それらの部分を置き換えるだけで済みます。はい、交換は比較的簡単です。これにより、プログラムの安定性と拡張性を最大限に確保できます。

JavaScript カプセル化には 3 つの基本モードがあります:

1. 合意優先の原則を使用し、すべてのプライベート変数は _

で始まります。
 <script type="text/javascript">
  /**
   * 使用约定优先的原则,把所有的私有变量都使用_开头
   */
  var Person = function (no, name, age)
  {
   this.setNo(no);
   this.setName(name);
   this.setAge(age);
  }
  Person.prototype = {
   constructor: Person,
   checkNo: function (no)
   {
    if (!no.constructor == "string" || no.length != 4)
     throw new Error("学号必须为4位");
   },
   setNo: function (no)
   {
    this.checkNo(no);
    this._no = no;
   }, 
   getNo: function ()
   {
    return this._no;
   setName: function (name)
   {
    this._name = name;
   }, 
   getName: function ()
   {
    return this._name;
   }, 
   setAge: function (age)
   {
    this._age = age;
   }, 
   getAge: function ()
   {
    return this._age;
   }, 
   toString: function ()
   {
    return "no = " + this._no + " , name = " + this._name + " , age = " + this._age;
   }
  };
  var p1 = new Person("0001", "小平果", "22");
  console.log(p1.toString());  //no = 0001 , name = 小平果 , age = 22
  p1.setNo("0003");
  console.log(p1.toString());  //no = 0003 , name = 小平果 , age = 22
  p1.no = "0004";
  p1._no = "0004";
  console.log(p1.toString()); //no = 0004 , name =小平果 , age = 22

 </script>
ログイン後にコピー

コードを読んだ後、_ で始まる変数をすべて入れても、そのままアクセスできます。これはカプセル化と言えますか?が優先されます。

このアンダースコアの使用はよく知られた命名規則であり、プロパティがオブジェクトの内部使用のみを目的としており、プロパティにアクセスしたり直接設定したりすると、予期しない結果が生じる可能性があることを示します。これにより、プログラマが誤って使用することを防ぐことができますが、意図的に使用することは防止できません。

このメソッドは、少なくともメンバー変数の getter メソッドと setter メソッドがオブジェクト内ではなくプロトタイプ内にあるため、全体的には良い選択です。これは不可能であり、カプセル化を厳密に実装する必要があると思われる場合は、2 番目の方法を検討してください。

2. カプセル化を厳密に実装する

<script type="text/javascript">
  /**
   * 使用这种方式虽然可以严格实现封装,但是带来的问题是get和set方法都不能存储在prototype中,都是存储在对象中的
   * 这样无形中就增加了开销
   */
  var Person = function (no, name, age)
  {
   var _no , _name, _age ;
   var checkNo = function (no)
   {
    if (!no.constructor == "string" || no.length != 4)
     throw new Error("学号必须为4位");
   };
   this.setNo = function (no)
   {
    checkNo(no);
    _no = no;
   };
   this.getNo = function ()
   {
    return _no;
   }
   this.setName = function (name)
   {
    _name = name;
   }

   this.getName = function ()
   {
    return _name;
   }

   this.setAge = function (age)
   {
    _age = age;
   }
   this.
     getAge = function ()
   {
    return _age;
   }

   this.setNo(no);
   this.setName(name);
   this.setAge(age);
  }
  Person.prototype = {
   constructor: Person,
   toString: function ()
   {
    return "no = " + this.getNo() + " , name = " + this.getName() + " , age = " + this.getAge();
   }
  }
  ;
  var p1 = new Person("0001", "小平果", "22");
  console.log(p1.toString());  //no = 0001 , name =小平果 , age = 22
  p1.setNo("0003");
  console.log(p1.toString());  //no = 0003 , name = 小平果 , age = 22
  p1.no = "0004";
  console.log(p1.toString()); //no = 0003 , name = 小平果 , age = 22

 </script>

ログイン後にコピー

これは、これまでに説明した他のオブジェクト作成モードとどのように違うのでしょうか? 上記の例では、オブジェクトのプロパティを作成および参照するときに常に this キーワードを使用します。この例では、これらの変数を var で宣言します。これは、それらが Person コンストラクター内にのみ存在することを意味します。 checkno 関数も同様に宣言されるため、プライベート メソッドになります。

これらの変数や関数にアクセスする必要があるメソッドは、Personal で宣言するだけで済みます。これらのメソッドはパブリックでありながらプライベートなプロパティおよびメソッドにアクセスできるため、特権メソッドと呼ばれます。これらの特権関数にオブジェクトの外部からアクセスするには、先頭にキーワード this を付けます。これらのメソッドは Person コンストラクターのスコープ内で定義されているため、プライベート プロパティにアクセスできます。これらのプロパティはパブリックではないため、this キーワードを使用せずに参照されます。すべての getter メソッドと assigner メソッドは、これを使用せずにこれらのプロパティを直接参照するように変更されました。

プライベート プロパティへの直接アクセスを必要としないメソッドは、元どおり Person.prototype で宣言できます。 toString() メソッドと同様です。プライベート メンバーへの直接アクセスを必要とするメソッドのみを特権メソッドとして設計する必要があります。ただし、各オブジェクト インスタンスにはすべての特権メソッドの新しいコピーが含まれるため、特権メソッドが多すぎるとメモリが大量に消費されます。

上記のコードを見ると、this. 属性名が削除され、カプセル化が厳密に実装されています。ただし、すべてのメソッドがオブジェクト内に存在します。これによりメモリのオーバーヘッドが増加します。

3. クロージャ

にカプセル化されます。
<script type="text/javascript">

  var Person = (function ()
  {
   //静态方法(共享方法)
   var checkNo = function (no)
   {
    if (!no.constructor == "string" || no.length != 4)
     throw new Error("学号必须为4位");
   };
   //静态变量(共享变量)
   var times = 0;

    //return the constructor.
   return function (no, name, age)
   {
    console.log(times++); // 0 ,1 , 2
    var no , name , age; //私有变量
    this.setNo = function (no) //私有方法
    {
     checkNo(no);
     this._no = no;
    };
    this.getNo = function ()
    {
     return this._no;
    }
    this.setName = function (name)
    {
     this._name = name;
    }

    this.getName = function ()
    {
     return this._name;
    }

    this.setAge = function (age)
    {
     this._age = age;
    }
    this.getAge = function ()
    {
     return this._age;
    }

    this.setNo(no);
    this.setName(name);
    this.setAge(age);
   }
  })();

  Person.prototype = {
   constructor: Person,
   toString: function ()
   {
    return "no = " + this._no + " , name = " + this._name + " , age = " + this._age;
   }
  };

  var p1 = new Person("0001", "小平果", "22");
  var p2 = new Person("0002", "abc", "23");
  var p3 = new Person("0003", "aobama", "24");


  console.log(p1.toString());  //no = 0001 , name = 小平果 , age = 22
  console.log(p2.toString());  //no = 0002 , name = abc , age = 23
  console.log(p3.toString()); //no = 0003 , name = aobama , age = 24

 </script>

ログイン後にコピー

上記のコードは、JS エンジンが読み込まれた後、 Person = 即時実行関数を直接実行します。その後、この関数はサブ関数を返します。これは、新しい Person によって呼び出されるコンストラクターであり、サブ関数は次のことを維持します。即時実行関数内の checkNo(no) と time への参照 (明らかなクロージャー)。したがって、checkNo と time は、3 つのオブジェクトを作成した後、それぞれ 0、1、2 になります。このアプローチの利点は、Personal で再利用する必要があるメソッドとプロパティをプライベートにして、オブジェクト間で共有できることです。

ここでの プライベート メンバー特権メンバー は、コンストラクター内で宣言されたままです。ただし、コンストラクターは通常の関数からインライン関数に変更され、それを含む関数の戻り値として変数 person に渡されます。これにより、静的プライベート メンバーを宣言できるクロージャが作成されます。外側の関数宣言の後にある空の括弧のペアは、コードがロードされるとすぐに関数を実行するために非常に重要です。この関数の戻り値は別の関数であり、それが Person 変数に代入されるため、Person はコンストラクターになります。この内部関数は、Person をインスタンス化するときに呼び出されます。外部関数は、静的メンバーを格納するために使用できるクロージャーを作成するためにのみ使用されます。

この例では、 Person のインスタンスごとにこのメソッドの新しいコピーを生成するのは意味がないため、 checkno は静的メソッドになるように設計されています。また、静的属性 time もあり、その関数 は、Person コンストラクター への呼び出しの合計数を追跡することです。

以上がこの記事の全内容です。カプセル化の意味をさらに学ぶのに役立つことを願っています。

このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、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)

AMD「Strix Halo」FP11のパッケージサイズを公開:Intel LGA1700と同等、Phoenixより60%大きい AMD「Strix Halo」FP11のパッケージサイズを公開:Intel LGA1700と同等、Phoenixより60%大きい Jul 18, 2024 am 02:04 AM

このWebサイトは7月9日、AMD Zen5アーキテクチャの「Strix」シリーズプロセッサには2つのパッケージングソリューションがあり、小型のStrixPointはFP8パッケージを使用し、StrixHaloはFP11パッケージを使用すると報じた。出典: videocardz 出典 @Olrak29_ 最新の事実は、StrixHalo の FP11 パッケージ サイズが 37.5mm*45mm (1687 平方ミリメートル) であり、これは Intel の AlderLake および RaptorLake CPU の LGA-1700 パッケージ サイズと同じであるということです。 AMD の最新の Phoenix APU は、サイズ 25*40mm の FP8 パッケージング ソリューションを使用しています。これは、StrixHalo の F

Java フレームワークにおけるデザイン パターンとアーキテクチャ パターンの違い Java フレームワークにおけるデザイン パターンとアーキテクチャ パターンの違い Jun 02, 2024 pm 12:59 PM

Java フレームワークにおけるデザイン パターンとアーキテクチャ パターンの違いは、デザイン パターンがソフトウェア設計における一般的な問題に対する抽象的な解決策を定義し、ファクトリ パターンなどのクラスとオブジェクト間の相互作用に焦点を当てていることです。アーキテクチャ パターンは、階層化アーキテクチャなどのシステム コンポーネントの編成と相互作用に焦点を当てて、システム構造とモジュールの間の関係を定義します。

Foxconn、AIワンストップサービスを構築、先進的な半導体パッケージング参入のためシャープに投資:2026年に生産開始、月産20,000枚のウエハーを生産する設計 Foxconn、AIワンストップサービスを構築、先進的な半導体パッケージング参入のためシャープに投資:2026年に生産開始、月産20,000枚のウエハーを生産する設計 Jul 18, 2024 pm 02:17 PM

このウェブサイトのニュースによると、経済日報は本日(7月11日)、フォックスコングループが、現在主流のパネルレベルファンアウトパッケージング(FOPLP)半導体ソリューションに焦点を当て、先進的なパッケージング分野に参入したと報じた。 1. 子会社のInnoluxに続き、Foxconn Groupが投資するシャープも日本のパネルレベルのファンアウトパッケージング分野への参入を発表し、2026年に生産開始される予定である。 Foxconn Group自体はAI分野で十分な影響力を持っており、先進的なパッケージングにおける欠点を補うことで、将来的により多くのAI製品の受注を促進する「ワンストップ」サービスを提供できるとしている。このウェブサイトの公開情報によると、フォックスコングループは現在シャープ株の10.5%を保有しており、現段階では保有を増減させる予定はなく、保有を維持すると述べている。

Java デザイン パターンにおけるデコレータ パターンの分析 Java デザイン パターンにおけるデコレータ パターンの分析 May 09, 2024 pm 03:12 PM

デコレータ パターンは、元のクラスを変更せずにオブジェクトの機能を動的に追加できる構造設計パターンです。抽象コンポーネント、具象コンポーネント、抽象デコレータ、具象デコレータの連携によって実装され、ニーズの変化に合わせてクラス機能を柔軟に拡張できます。この例では、ミルクとモカのデコレーターが総額 2.29 ドルで Espresso に追加されており、オブジェクトの動作を動的に変更するデコレーター パターンの力を示しています。

PHP設計パターンの実践事例分析 PHP設計パターンの実践事例分析 May 08, 2024 am 08:09 AM

1. ファクトリ パターン: オブジェクト作成とビジネス ロジックを分離し、ファクトリ クラスを通じて指定された型のオブジェクトを作成します。 2. オブザーバー パターン: サブジェクト オブジェクトが状態の変化をオブザーバー オブジェクトに通知できるようにし、疎結合とオブザーバー パターンを実現します。

デザインパターンがコードメンテナンスの課題にどのように対処するか デザインパターンがコードメンテナンスの課題にどのように対処するか May 09, 2024 pm 12:45 PM

デザイン パターンは、再利用可能で拡張可能なソリューションを提供することで、コード メンテナンスの課題を解決します。 オブザーバー パターン: オブジェクトがイベントをサブスクライブし、イベントが発生したときに通知を受信できるようにします。ファクトリ パターン: 具象クラスに依存せずにオブジェクトを作成するための集中的な方法を提供します。シングルトン パターン: クラスには、グローバルにアクセス可能なオブジェクトの作成に使用されるインスタンスが 1 つだけ存在することが保証されます。

Java 設計パターンにおけるアダプター パターンの素晴らしい使用法 Java 設計パターンにおけるアダプター パターンの素晴らしい使用法 May 09, 2024 pm 12:54 PM

アダプター パターンは、互換性のないオブジェクトが連携できるようにする構造設計パターンであり、オブジェクトがスムーズに対話できるように、あるインターフェイスを別のインターフェイスに変換します。オブジェクト アダプタは、適応されたオブジェクトを含むアダプタ オブジェクトを作成し、ターゲット インターフェイスを実装することにより、アダプタ パターンを実装します。実際のケースでは、クライアント (MediaPlayer など) はアダプター モードを通じて高度な形式のメディア (VLC など) を再生できますが、クライアント自体は通常のメディア形式 (MP3 など) のみをサポートします。

PHP デザイン パターン: テスト駆動開発の実践 PHP デザイン パターン: テスト駆動開発の実践 Jun 03, 2024 pm 02:14 PM

TDD は、高品質の PHP コードを作成するために使用されます。その手順には、テスト ケースを作成し、期待される機能を記述し、テスト ケースを失敗させることが含まれます。過度な最適化や詳細な設計を行わずに、テスト ケースのみが通過するようにコードを記述します。テスト ケースが合格したら、コードを最適化およびリファクタリングして、可読性、保守性、およびスケーラビリティを向上させます。

See all articles