JavaScriptにプライベート変数を実装します
World Wide Webに力を与えるプログラミング言語であるJavaScriptは、1995年5月にBrendan Eichが作成して以来、広く使用された多用途のテクノロジーになりました。成功したにもかかわらず、かなりの批判、特にいくつかの機能も受けています。たとえば、オブジェクトはインデックスとして使用されると文字列にキャストされます。1== "1"はtrue、またはthis
キーワードを混乱させる悪名高いものを返します。ただし、特に興味深い機能の1つは、さまざまなプライバシーを実装するさまざまな手法の存在です。
現在、JavaScriptにプライベート変数を直接作成する方法はありません。他の言語では、 private
キーワードまたは二重アンダースコアを使用でき、すべてが正常に機能しますが、JavaScriptでは、可変プライバティネスには、予想される機能よりも言語の緊急機能により似た機能があります。最初に質問の背景を紹介しましょう。
var
キーワード
2015年まで、基本的に変数を作成する1つの方法しかありませんでしたが、それがvar
キーワードでした。 var
は関数スコープされています。つまり、このキーワードにインスタンス化された変数は、関数内のコードによってのみアクセスできます。関数が外部または本質的に「グローバル」である場合、変数が定義された後に実行されたすべてのものによって変数にアクセスできます。定義の前に同じスコープで変数にアクセスしようとすると、エラーの代わりにundefined
なります。これは、 var
キーワードの「アップグレード」方法によるものです。
//グローバル範囲で「A」を定義します var a = 123; //関数範囲で「B」を定義します (関数() { console.log(b); // =>プロモーションにより、「未定義」がエラーではなく返されます。 var b = 456; })(); console.log(a); // => 123 console.log(b); //「b」に関数範囲外からアクセスできないため、「参照エラー」例外をスローします。
ES6変数の誕生
2015年には、ES6/ES2015が公式にリリースされ、2つの新しい変数キーワードが続きました。Let const
let
どちらもブロックスコープされています。つまり、これらのキーワードで作成された変数は、同じブラケットのペア内のすべてのものによってアクセスできます。 var
と同じですが、 let
およびconst
変数には、ループ、関数、ステートメント、ブラケットなどのブロックスコープの外側にアクセスできません。
const a = 123; //スコープの例#1をブロックします if(true){ const b = 345; } //スコープの例#2をブロックします { const c = 678; } console.log(a); // 123 console.log(b); //「B」にブロックスコープの外側からアクセスできないため、「参照エラー」をスローします。 console.log(c); //「B」にブロックスコープの外側からアクセスできないため、「参照エラー」をスローします。
スコープの外側のコードは変数にアクセスできないため、プライベートの出現が得られます。さまざまな方法で実装するためのいくつかの手法を紹介します。
関数を使用します
JavaScriptの関数もブロックであるため、すべての可変キーワードはそれらと連携します。さらに、「モジュール」と呼ばれる非常に有用なデザインパターンを実装できます。
モジュール設計モード
Googleは、「モジュール」を定義するためにオックスフォード辞書に依存しています。
このプログラムは、そこから構築されるか、複雑な活動のさまざまであるが相互に関連するユニットのいずれかを分析する場合があります。
- 「モジュール」定義1.2
モジュールの設計パターンは、パブリックコンポーネントとプライベートコンポーネントを組み合わせてプログラムをより小さなコンポーネントに分解できるため、JavaScriptで非常に役立ち、「カプセル化」と呼ばれるプロセスを通じて別のプログラムパーツがアクセスできるもののみを公開するためです。このようにして、私たちは使用する必要があるもののみを公開し、見る必要のないものを非表示にします。関数範囲を活用することでこれを行うことができます。
const carmodule =()=> { Milesdriven = 0とします。 速度= 0とします。 const Accelerate =(antom)=> { 速度=額; milesdriven = speed; } const getMilesDriven =()=> MilesDriven; //「戻り」キーワードを使用して、どのコンテンツが公開され、どのコンテンツが非表示になっているかを制御できます。この場合、Accelerate()およびgetMilesdriven()関数のみを公開します。 戻る { 加速、 getMilesDriven } }; const testcarmodule = carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven());
このようにして、走行距離と加速を取得できますが、この場合はユーザーがアクセス速度を必要としないため、 accelerate()
とgetMilesDriven()
メソッドのみを公開することで非表示にできます。基本的に、 speed
同じ範囲内のコードによってのみアクセスできるため、プライベート変数です。この場合、プライベート変数の利点が明らかになり始めます。変数、関数、またはその他の内部コンポーネントにアクセスする機能を削除すると、使用すべきではない他者が誤って他者が誤って使用している表面積を減らします。
別の方法
この2番目の例では、 this
キーワードの追加に気付くでしょう。 ES6矢印関数(=>)と従来の関数(){}には違いがあります。 function
キーワードを使用すると、 this
使用できます。これは関数自体にバインドされ、矢印関数はthis
キーワードのどのタイプの使用を許可しません。どちらもモジュールを作成するための同様に効果的な方法です。コアのアイデアは、アクセスする必要がある部品を開示し、対話するべきではない他の部品を保持することです。そのため、パブリックデータとプライベートデータの両方があります。
function carmodule(){ Milesdriven = 0とします。 速度= 0とします。 //この場合、代わりに「この」キーワードを使用します。 // Carmoduleを指します this.Accelerate =(antom)=> { 速度=額; milesdriven = speed; } this.getMilesDriven =()=> MilesDriven; } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven());
ES6クラス
クラスは、ES6のもう1つの新機能です。クラスは本質的に構文砂糖です。つまり、依然として機能ですが、より簡単に表現された形に「美化」する場合があります。クラスの場合、コードにいくつかの大きな変更が加えられない限り、変動的なプライベート(現在のところ)はほとんど不可能です。
クラスの例を見てみましょう。
クラスカーモジュール{ /* Milesdriven = 0; 速度= 0; */ constructor(){ this.milesdriven = 0; this.speed = 0; } 加速(量){ this.speed =額; this.milesdriven = this.speed; } getMilesDriven(){ this.milesdrivenを返します。 } } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven());
最初に注意すべきことは、 milesDriven
とspeed
変数がconstructor()
関数にあることです。コンストラクターの外側の変数を定義することもできます(コードコメントに示されているように)が、とにかく機能的に同じです。問題は、これらの変数が公開され、クラス外の要素によってアクセスできることです。
この問題のいくつかの解決策を見てみましょう。
下線を使用します
協力者が壊滅的な間違いを犯さないようにするための状況では、変数のプレフィックスとしてアンダースコア(_)を使用して、外側に「目に見える」が、開発者に「この変数に触れないでください」を合図するのに十分です。したがって、たとえば、次のようになりました。
//これはクラスの新しいコンストラクターです。コンストラクター()の外側の次のコンテンツとして表現できることに注意してください。 /* _milesdriven = 0; _Speed = 0; */ constructor(){ this._milesdriven = 0; this._speed = 0; }
これは特定のユースケースで機能しますが、多くの点で理想的ではないと言っても安全です。変数にアクセスすることもできますが、変数名を変更する必要もあります。
すべてをコンストラクターに入れます
技術的には、クラスでプライベート変数を使用する方法があります。これは、すべての変数とメソッドをconstructor()
関数に配置することです。見てみましょう。
クラスカーモジュール{ constructor(){ Milesdriven = 0とします。 速度= 0とします。 this.Accelerate =(antom)=> { 速度=額; milesdriven = speed; } this.getMilesDriven =()=> MilesDriven; } } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven()); console.log(testcarmodule.speed); //未定義 - 実際の変動プライバシーがあります。
このアプローチは、意図的に開示されていない変数への直接アクセスがないため、真の変動プライバシーを実装します。問題は、私たちが今、私たちのものと比較して非常に良いコードを見ていないことであり、クラスを使用するときに構文砂糖の利点を破ることです。現時点では、 function()
メソッドを使用することもできます。
WeakMapを使用します
また、 WeakMap()
使用するためのプライベート変数を作成するためのより創造的な方法もあります。 Map
と同様に聞こえるかもしれませんが、2つは非常に異なります。マッピングはあらゆるタイプの値をキーとして取得できますが、 WeakMap
オブジェクトのみを受け入れ、ガーベージがオブジェクトキーを収集するときにWeakMap
の値を削除します。さらに、 WeakMap
反復することはできません。つまり、値にアクセスするにはオブジェクトキーへの参照にアクセスする必要があります。これにより、変数は実際には見えないため、プライベート変数の作成に非常に役立ちます。
クラスカーモジュール{ constructor(){ this.data = new weakMap(); this.data.set(this、{ マイルズドライブン:0、 速度:0 }); this.getMilesdriven =()=> this.data.get(this).Milesdriven; } 加速(量){ //このバージョンでは、代わりにWeakMapを作成し、//「この」キーワードをキーとして使用します。 const data = this.data.get(this); const速度= data.speed額; const milesdriven = data.milesdriven data.speed; this.data.set({speed、milesdriven}); } } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven()); console.log(testcarmodule.data); // => weakmap {[items nown nowns]} - このデータは、外部から簡単にアクセスできません!
このソリューションは、データの偶発的な使用を防ぐのに適していますが、 this
CarModule
に置き換えることで外部からアクセスできるため、実際にはプライベートではありません。さらに、それはかなりの複雑さを追加するため、最もエレガントなソリューションではありません。
競合を防ぐためにシンボルを使用します
目的が名前の競合を防ぐことである場合、 Symbol
を使用して有用なソリューションを提供できます。これらは本質的に一意の値として機能する可能性のあるインスタンスであり、独自のインスタンスを除いて他の値に匹敵することはありません。実際のアプリケーションの例は次のとおりです。
クラスカーモジュール{ constructor(){ this.speedKey = symbol( "speedkey"); this.milesdrivenkey = symbol( "milesdrivenkey"); この[this.speedkey] = 0; この[this.milesdrivenkey] = 0; } 加速(量){ //このデータは、予期せずにアクセスすることはほとんど不可能です。決してプライベートではありません。 //しかし、このモジュールを実装する人から離れています。 この[this.speedKey] =額; この[this.milesdrivenkey] = this [this.speedkey]; } getMilesDriven(){ これを返します[this.milesdrivenkey]; } } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven()); console.log(testcarmodule.speed); // =>未定義 - 変数にアクセスするには、内部キーにアクセスする必要があります。 アンダースコアソリューションと同様に、このアプローチは、混乱を防ぐために義務の命名に多かれ少なかれ依存しています。
TC39プライベートクラスフィールド提案
最近、クラスに私的変数を導入する新しい提案が提案されました。簡単です:変数名を準備し、プライベートになります。追加の構造変更は必要ありません。
クラスカーモジュール{ #Speed = 0 #milesdriven = 0 加速(量){ //このデータは、予期せずにアクセスすることはほとんど不可能です。 これ。#speed =額; これ。#milesdriven = speed; } getMilesDriven(){ これを返してください。#milesdriven; } } const testcarmodule = new Carmodule(); testcarmodule.accelerate(5); testcarmodule.accelerate(4); console.log(testcarmodule.getMilesdriven()); console.log(testcarmodule.speed); // =>未定義 - 変数にアクセスするには、内部キーにアクセスする必要があります。
プライベートクラスの機能は現実になり、非常に優れたブラウザのサポートがあります。
結論は
これは、JavaScriptにプライベート変数を実装するさまざまな方法の要約です。 「正しい」アプローチはありません。これらの方法は、さまざまな要件、既存のコードベース、およびその他の制約に適しています。それぞれのアプローチには利点と短所がありますが、最終的には、問題を効果的に解決する限り、すべてのアプローチは等しく効果的です。
読んでくれてありがとう!これにより、JavaScriptコードを改善するためにスコープと変動するプライバシーを適用する方法に関する洞察が得られることを願っています。これは、多くの異なる方法をサポートし、コードを使いやすくエラーできない強力なテクノロジーです。より良い気持ちを得るために、自分でいくつかの新しい例を試してください。
以上がJavaScriptにプライベート変数を実装しますの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ホットAIツール

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

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

Undress AI Tool
脱衣画像を無料で

Clothoff.io
AI衣類リムーバー

Video Face Swap
完全無料の AI 顔交換ツールを使用して、あらゆるビデオの顔を簡単に交換できます。

人気の記事

ホットツール

メモ帳++7.3.1
使いやすく無料のコードエディター

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

ゼンドスタジオ 13.0.1
強力な PHP 統合開発環境

ドリームウィーバー CS6
ビジュアル Web 開発ツール

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

ホットトピック











それは' Vueチームにそれを成し遂げてくれておめでとうございます。それは大規模な努力であり、長い時間がかかったことを知っています。すべての新しいドキュメントも同様です。

最近のビットコインの価格が20k $ $ USDを超えており、最近30Kを破ったので、イーサリアムを作成するために深く掘り下げる価値があると思いました

私はこの非常に正当な質問で誰かに書いてもらいました。 Leaは、ブラウザから有効なCSSプロパティ自体を取得する方法についてブログを書いています。それはこのようなものです。

先日、Corey Ginnivanのウェブサイトから、この特に素敵なビットを見つけました。そこでは、スクロール中にカードのコレクションが互いに積み重ねられていました。

これらのデスクトップアプリがいくつかあり、目標があなたのサイトをさまざまな次元ですべて同時に表示しています。たとえば、書くことができます

WordPressエディターでユーザーに直接ドキュメントを表示する必要がある場合、それを行うための最良の方法は何ですか?

フレックスレイアウトの紫色のスラッシュ領域に関する質問フレックスレイアウトを使用すると、開発者ツールなどの混乱する現象に遭遇する可能性があります(D ...
