序文最近、インタビューの質問を見ました。もちろん、この記事のタイトルである「Ajax 同時リクエスト制御」ですが、とても興味深いと思います。コミュニティで調べたところ、ByteDance からのインタビューの質問のはずです。多くの大物がこれを要約しています。私はそれらをすべて読んだので、自分で要約してみたいと思います。コードは記事の最後に掲載します。何か間違っている点があれば、指摘してください。 Ajax シリアルおよびパラレル
上記のシミュレーションはPromise.allに基づく並列操作を実装しており、出力結果は以下のとおりです。 これが終わりであり、存在しないと感じますか?さて、いよいよ本題です。ページが同時に何万ものリクエストを送信し、そのすべてが成功した後にいくつかの操作を実行する必要がある状況を想像してみましょう。結果はどうなるでしょうか?コードを実行できず、メモリがオーバーフローします。残念ながら、ここでこの記事のトピックに戻ります。同時 Ajax リクエストを制御するにはどうすればよいでしょうか?一度に一定数のリクエストだけを出力し、すべてが成功するまで続けるように依頼しました。次に、この操作を 2 つの方法で実装します。読者の皆さんのアドバイスをお待ちしています。 Ajaxの同時リクエスト制御のための2つのソリューションPromiseベースの再帰次の 2 つの方法は、どちらも上図の Tasks 配列を必要とします。覚えておいてください。Promise に基づく最初の方法は、次のような考え方です。同時実行プールを渡すと、ワークスペースのプールが作成されます。各ワークスペースは、実行する対応するタスク (リクエスト) を取得し、成功したら保存し、ワークスペースにタスクがなくなるまでタスク (リクエスト) を取得し続けます。もちろん、失敗した場合は直接終了します。これが一般的な考え方です。以下のコードの各行にコメントを付けました。どうぞご了承ください。 クラスベースの実装2 番目の方法はクラスに基づいています。上記との違いは、この方法ではワークスペースが 1 つしか作成されないことです。基本的な考え方は、タスク (リクエスト) を実行するためのワークスペースを作成し、すべてのタスクをそこにプッシュしますが、毎回、対応する数の同時タスクしか実行できません。同時タスクの数より少ない場合は、タスク (リクエスト) がなくなるまでタスクを取得して実行し続けます。これで完了です。具体的な実装は次のとおりです。 コードショーケースこれら 2 つのメソッドの実装コードを以下に示します。 const delay = 関数 delay(間隔) { 新しい Promise((res,rej) => { を返す タイムアウトを設定する(() => { res(間隔) }, 間隔); }) } タスクを = [() => { 戻り遅延(1000) },() => { 返品遅延(1003) },() => { 返品遅延(1005) },() => { 返品遅延(1002) },() => { 返品遅延(1004) },() => { 返品遅延(1006) }] // Promise.all を通じて並列処理を実装する Promise.all(tasks.map(task => task())).then(res => { コンソールログ(res); }) // Promise に基づいて関数 creatRequest(tasks,pool) を実装します { // 毎回送信されるリクエストの数はプールによって制御されます プール = プール || 5 // 各リクエストの結果を保存するために使用されます(順番に保存されます) 結果 = [] とします。 // together はワークスペースを作成するために使用されます。pool が渡されると、それに応じて複数のワークスペースが作成されます。// つまり、pool の長さと null の値を持つ配列を作成します。together = new Array(pool).fill(null), // インデックスは毎回取得されるタスク値です。index = 0; 一緒に = 一緒に.map(() => { // Promise に基づく管理 return new Promise((resolve,reject) => { // 関数を作成し、すぐに実行する const run = function run() { // タスクプールが空の場合、リクエストが正常に送信されたことを意味します if(index >=tasks.length) { 解決する() 戻る } // まず、現在の成功したリクエストの結果を保存するためのインデックスを保存します。let old_index = index, // 現在送信されているリクエストを取得し、インデックスを累積します。そのため、インデックスは上記に保存されます。 // ここでは、index++ が最初に計算されてから累積されますが、++index はその逆で、最初に累積されてから計算されます。task = tasks[index++]; // リクエストを実行する task().then(result => { // 成功した結果を保存する results[old_index] = result // 再帰的に実行を続行します。つまり、タスクをワークスペースに取得して実行を続行します run(); }).catch(理由 => { 拒否(理由) }) } // すぐにrun()を実行する }) }) // Promise.all を使用してワークスペースを制御します。つまり、一度に 2 つのリクエストを同時に実行します。 return Promise.all(together).then(() => results) } createRequest(タスク,2).then(結果 => { // 全体が成功するにはすべてが成功する必要があるので、結果を順番に保存します。console.log('success',results); }).catch(解決 => { // いずれか 1 つでも失敗すると、システム全体が失敗します console.log('failed'); }) // クラスに基づいて関数 creatRequest(tasks,pool,callback) を実装します { // パラメータの制限と検証 if(typeof pool === 'function') { コールバック = プール; プール = 5 } if (typeof pool !== 'number') プール = 5 if (typeof callback !== 'function') callback = function () {} //------ クラスタスクキュー { // 実行回数 = 0; // すべてのタスクをキューに入れる queue = []; // タスク(リクエスト)の実行結果を保存します。 results = []; タスクをプッシュします。 自分 = これ // タスクをワークスペースにプッシュします。self.queue.push(task) // リクエストを送信するロジックを実行する self.next() } 次() { 自分 = これ // 実行中のタスク数が同時実行数より少ない場合、タスクの実行を継続します while(self.runing < pool && self.queue.length) { 自己実行++; // これはタスクを取得して削除するのと同じです。let task = self.queue.shift(); // リクエストを実行する task().then(result => { //実行結果を保存する self.results.push(result) }).finally(() => { // 実行中の項目の数をクリアする self.runing-- // リクエストの実行を続行する self.next() }) } // タスクがない場合はループが終了します if(self.runing === 0) callback(self.results) } } // インスタンス化 let TQ = new TaskQueue() タスクごとにタスクを実行します。 } リクエストを作成します(タスク、2、結果=> { console.log(結果); }) 要約する上記は、この一連のインタビューの質問の要約です。私自身もメモしました。今後もフロントエンドの記事を更新し続けます。最後に、フロントエンドの友人全員が学習を継続し、スキルを継続的に向上させることができることを願っています。さあ、若者よ! ! ! JS ベースの Ajax 同時リクエスト制御の実装方法に関するこの記事はこれで終わりです。JS による Ajax 同時リクエスト制御の実装に関するより関連性の高いコンテンツについては、123WORDPRESS.COM の以前の記事を検索するか、以下の関連記事を引き続き参照してください。今後とも 123WORDPRESS.COM をよろしくお願いいたします。 以下もご興味があるかもしれません:
|
>>: MySql5.x を MySql8.x にアップグレードする方法と手順
任意の数のステートメントを関数を通じてカプセル化することができ、いつでもどこでも呼び出して実行できま...
背景私は新しいプロジェクト チームに配属されたので、プロジェクトでは js を使用する必要があります...
目次序文1. 何ですか2. Node.jsでEventEmitterを使用する方法3. 実施プロセス...
目次コンポーネントの分解左パネル右パネル入力パラメータの分解小道具スロット具体的な実装ドラッグする方...
NFSが提供するサービスマウント: サーバー上で /usr/sbin/rpc.mountd サーボ ...
1. レスポンシブな Web を開発するには、ページを画面サイズに適応させる必要があります。前の記...
この記事では、参考までにMySQL 5.7.17圧縮版のインストール手順を紹介します。具体的な内容は...
まず、MySQL とは何かを理解しましょう。 MySQL は、スウェーデンの会社 MySQL AB ...
Azure Container Registry は、Docker Registry 2.0 仕様に...
序文システム領域の使用量が大きすぎて消去する必要がある場合、または特定のファイルを消去する必要がある...
justify-content:space-betweenレイアウトを使用する場合、要素の最後の行に...
JSON データを美しいインデント形式で表示するには、最も単純な JSON.stringify 関...
1.公式サイトからダウンロードして解凍する参考: 2. 環境変数を設定するMYSQL_HOMEをMy...
感想:私はバックエンド開発者です。静的 (HTML) ページを取得すると、ページ構造と命名規則が極端...
オプションに属性 selected = "selected" を追加すると、それ...