JS Proxyのメリットと利用シーン
車を運転する人は車の構造を理解していないことが多いですが、車の構造を深く理解することでさらに大きな効果が得られる可能性があります。
序文
vue3.x のニュースが増えるにつれて、
proxy についての議論も増えています。
Object.defineProperty と比較した場合、
proxy の違い、利点、用途は何ですか?この記事では、
Object.defineProperty
について簡単に紹介します。proxy について説明する前に、
Object.defineProperty を確認しましょう。ご存知のとおり、
vue2.x とそれ以前のバージョンでは、
Object.defineProperty を使用してデータの双方向バインドを実現しています。単純に実装しましょう
function observer(obj) { if (typeof obj === 'object') { for (let key in obj) { defineReactive(obj, key, obj[key]) } } } function defineReactive(obj, key, value) { //针对value是对象,递归检测 observer(value) //劫持对象的key Object.defineProperty(obj, key, { get() { console.log('获取:' + key) return value }, set(val) { //针对所设置的val是对象 observer(val) console.log(key + "-数据改变了") value = val } }) } let obj = { name: '守候', flag: { book: { name: 'js', page: 325 }, interest: ['火锅', '旅游'], } } observer(obj)
コンソール、正常に動作するように見えます
Object.defineProperty 問題は次のとおりです。
gender を追加すると、実行中、
observer(obj) にはこの属性がないため、監視できません。
を追加すると削除された属性は監視できません。vue
は
$setを使用して操作する必要があります。
$setObject.defineProperty
は内部的に操作にも使用されます
##問題 2. 配列の変更を監視できません
##上の図からわかるように、実際には配列属性は正常に変更されていますが、監視することはできません
Object.defineProperty
を使用してオブジェクトのプロパティがハイジャックされます。走査されるオブジェクト レベルが比較的深い場合は、時間がかかり、パフォーマンスの問題が発生する可能性もあります proxy
proxy
の場合、mdn の説明は次のとおりです: オブジェクトは、基本的な操作 (属性の検索、割り当て、列挙など) のカスタム動作を定義するために使用されます。 、関数呼び出しなど)簡単に言うと、ターゲット オブジェクトにインターセプトのレイヤーを設定できます。ターゲット オブジェクトに対してどのような操作が実行される場合でも、このインターセプト層を通過する必要があります。
proxy
はObject.defineProperty よりも使いやすいようです。実際、それだけです。プロキシを使用して上記のコードを書き換えて試してみましょう
function observerProxy(obj) { let handler = { get(target, key, receiver) { console.log('获取:' + key) // 如果是对象,就递归添加 proxy 拦截 if (typeof target[key] === 'object' && target[key] !== null) { return new Proxy(target[key], handler) } return Reflect.get(target, key, receiver) }, set(target, key, value, receiver) { console.log(key + "-数据改变了") return Reflect.set(target, key, value, receiver) } } return new Proxy(obj, handler) } let obj = { name: '守候', flag: { book: { name: 'js', page: 325 }, interest: ['火锅', '旅游'], } } let objTest = observerProxy(obj)
同じ効果
##そして、Object.defineProperty Things属性
の追加などの実行できない操作は、
も監視できます。
1.
インターセプトされるのはオブジェクトのプロパティです。これにより、元のオブジェクトが変更されます。
proxy はオブジェクト全体をインターセプトし、元のオブジェクトを変更せずに new を通じて新しいオブジェクトを生成します。 2.
proxy
上記の get および set に加えて、他にも 11 個のインターセプト メソッドがあります。プロキシを選択するにはさまざまな方法があり、配列の監視、オブジェクト プロパティの追加と削除の監視など、
ではできない一部の操作を監視することもできます。 プロキシの使用シナリオ
プロキシの使用シナリオについては、スペースの制限のため、ここでは単にいくつかを列挙しますが、さらに多くのシナリオを列挙することができます。私の github ノートまたは mdn に従ってください。
これを見ると、この 2 つの違いと proxy
の利点がすでにわかりました。しかし、開発では、
はどのようなシナリオで使用できますか? 発生する可能性のあるいくつかの状況を次に示します 負のインデックス配列
## を使用する場合#splice(-1)、slice(-1)
およびその他の API では、負の数値を入力すると、配列の最後の項目が配置されますが、通常の配列上にあり、負の数になります。数字は使用できません。[1,2,3][-1] このコードでは 3 を出力できません。上記のコードを出力 3 にするには、
proxy を使用することもできます。
rreeee<h3 id="span-style-font-size-px-表单校验-span"><span style="font-size: 16px;">表单校验</span></h3>
<p>在对表单的值进行改动的时候,可以在 <code>set
里面进行拦截,判断值是否合法
let ecValidate = { set(target, key, value, receiver) { if (key === 'age') { //如果值小于0,或者不是正整数 if (value < 0 || !Number.isInteger(value)) { throw new TypeError('请输入正确的年龄'); } } return Reflect.set(target, key, value, receiver) } } let obj = new Proxy({ age: 18 }, ecValidate) obj.age = 16obj.age = '少年'
增加附加属性
比如有一个需求,保证用户输入正确身份证号码之后,把出生年月,籍贯,性别都添加进用户信息里面
众所周知,身份证号码第一和第二位代表所在省(自治区,直辖市,特别行政区),第三和第四位代表所在市(地级市、自治州、盟及国家直辖市所属市辖区和县的汇总码)。第七至第十四位是出生年月日。低17位代表性别,男单女双。
const PROVINCE_NUMBER = { 44 : '广东省', 46 : '海南省' } const CITY_NUMBER = { 4401 : '广州市', 4601 : '海口市' } let ecCardNumber = { set(target, key, value, receiver) { if (key === 'cardNumber') { Reflect.set(target, 'hometown', PROVINCE_NUMBER[value.substr(0, 2)] + CITY_NUMBER[value.substr(0, 4)], receiver) Reflect.set(target, 'date', value.substr(6, 8), receiver) Reflect.set(target, 'gender', value.substr( - 2, 1) % 2 === 1 ? '男': '女', receiver) } return Reflect.set(target, key, value, receiver) } } let obj = new Proxy({ cardNumber: '' }, ecCardNumber)
数据格式化
比如有一个需求,需要传时间戳给到后端,但是前端拿到的是一个时间字符串,这个也可以用 proxy
进行拦截,当得到时间字符串之后,可以自动加上时间戳。
let ecArrayProxy = { get(target, key, receiver) { let _index = key < 0 ? target.length + Number(key) : key return Reflect.get(target, _index, receiver) } } let arr = new Proxy([1, 2, 3], ecArrayProxy)
推荐教程:《JS教程》
以上がJS Proxyのメリットと利用シーンの詳細内容です。詳細については、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.jsでBootstrapを使用すると、5つのステップに分かれています。ブートストラップをインストールします。 main.jsにブートストラップをインポートしますブートストラップコンポーネントをテンプレートで直接使用します。オプション:カスタムスタイル。オプション:プラグインを使用します。

HTMLテンプレートのボタンをメソッドにバインドすることにより、VUEボタンに関数を追加できます。 VUEインスタンスでメソッドを定義し、関数ロジックを書き込みます。

Vue.jsの監視オプションにより、開発者は特定のデータの変更をリッスンできます。データが変更されたら、Watchはコールバック関数をトリガーして更新ビューまたはその他のタスクを実行します。その構成オプションには、すぐにコールバックを実行するかどうかを指定する即時と、オブジェクトまたは配列の変更を再帰的に聴くかどうかを指定するDEEPが含まれます。

VUEマルチページ開発は、VUE.JSフレームワークを使用してアプリケーションを構築する方法です。アプリケーションは別々のページに分割されます。コードメンテナンス:アプリケーションを複数のページに分割すると、コードの管理とメンテナンスが容易になります。モジュール性:各ページは、簡単に再利用および交換するための別のモジュールとして使用できます。簡単なルーティング:ページ間のナビゲーションは、単純なルーティング構成を介して管理できます。 SEOの最適化:各ページには独自のURLがあり、SEOに役立ちます。

vue.jsでJSファイルを参照するには3つの方法があります。タグ;; mounted()ライフサイクルフックを使用した動的インポート。 Vuex State Management Libraryを介してインポートします。

vue.jsには、前のページに戻る4つの方法があります。$ router.go(-1)$ router.back()outes&lt; router-link to =&quot;/&quot; Component Window.history.back()、およびメソッド選択はシーンに依存します。

Vue.jsには配列とオブジェクトを通過するには3つの一般的な方法があります。V-Forディレクティブは、各要素をトラバースしてテンプレートをレンダリングするために使用されます。 V-BindディレクティブをV-Forで使用して、各要素の属性値を動的に設定できます。 .mapメソッドは、配列要素を新しい配列に変換できます。

VUEにDIV要素をジャンプするには、VUEルーターを使用してルーターリンクコンポーネントを追加するには、2つの方法があります。 @clickイベントリスナーを追加して、これを呼び出します。$ router.push()メソッドをジャンプします。
