[解決済み] JavaScriptで[].forEach.call()は何をするのですか?
質問
コードのいくつかのスニペットを見ていたところ、空の配列に適用される forEach でノード リスト上で関数を呼び出す複数の要素を見つけました。
たとえば、私は次のようなものを持っています。
[].forEach.call( document.querySelectorAll('a'), function(el) {
// whatever with the current node
});
と書いているのですが、どのように動作するのか理解できません。どなたか、forEachの前の空の配列の動作と、どのように
call
がどのように機能するのか説明できますか?
どのように解決するのですか?
[]
は配列です。
この配列は全く使われません。
ページに置かれているのは、配列を使うことで配列のプロトタイプにアクセスできるためで、例えば
.forEach
.
と打つより早いです。
Array.prototype.forEach.call(...);
次は
forEach
は関数を入力とする関数です...
[1,2,3].forEach(function (num) { console.log(num); });
...そして、各要素に対して
this
(ここで
this
は配列のようなもので、その中に
length
のようにその部分にアクセスすることができます。
this[1]
のように)3つのものを渡します。
- 配列の要素
-
要素のインデックス (3番目の要素なら
2
) - 配列への参照
最後に
.call
は関数が持つプロトタイプです(他の関数に呼び出される関数です)。
.call
はその最初の引数を取り
this
を通常の関数内で
call
を最初の引数として渡します (
undefined
または
null
は
window
を使用します。quot;strict-mode")であれば、あなたが渡したものが使用されます。残りの引数は、元の関数に渡されます。
[1, 2, 3].forEach.call(["a", "b", "c"], function (item, i, arr) {
console.log(i + ": " + item);
});
// 0: "a"
// 1: "b"
// 2: "c"
したがって、あなたは素早く呼び出す方法を作成し
forEach
関数を呼び出す手っ取り早い方法を作っているわけで、そのために
this
を空の配列からすべての
<a>
タグのリストに変換し、それぞれの
<a>
の順で、提供された関数を呼び出していることになります。
EDIT
論理的な結論/後始末
この解決策はハック的で見苦しいので、関数型プログラミングの試みは破棄し、毎回、手動でインラインループに固執することを提案する記事へのリンクが以下にあります。
私が言いたいのは
.forEach
は対応するものに比べて、あまり役に立ちません。
.map(transformer)
,
.filter(predicate)
,
.reduce(combiner, initialValue)
のいずれかにアクセスしながら、(配列ではなく)外界をn回変更したい場合、この方法はまだ役に立ちます。
arr[i]
または
i
.
では、Mottoは明らかに才能と知識のある人物であり、私は自分が何をしているか/どこへ行くかを知っていると想像したいのですが(今も昔も... ...他の時は頭を使って学んでいます)、この格差にはどう対処すればいいのでしょうか?
その答えは実にシンプルで、ボブおじさんもクロックフォード卿も、その見落としのために顔面蒼白になるようなものです。
クリーンアップする .
function toArray (arrLike) { // or asArray(), or array(), or *whatever*
return [].slice.call(arrLike);
}
var checked = toArray(checkboxes).filter(isChecked);
checked.forEach(listValues);
さて、もしあなたが自分でこれをする必要があるかどうか疑問に思っているなら、答えは「いいえ」かもしれません...。
この正確なことは、... ...最近の高次機能を持つすべての(?)ライブラリによって行われています。
もしあなたがlodashやunderscore、あるいはjQueryを使っているなら、それらはすべて要素のセットを取って、あるアクションをn回実行する方法を持っているはずです。
そのようなものを使っていないのであれば、是非とも自分で書いてください。
lib.array = (arrLike, start, end) => [].slice.call(arrLike, start, end);
lib.extend = function (subject) {
var others = lib.array(arguments, 1);
return others.reduce(appendKeys, subject);
};
ES6(ES2015)以降のアップデートについて
だけでなく
slice( )
/
array( )
/しかし、比較的近い将来の ES6+ ブラウザで操作したり、今日 Babel で "transpiling" する余裕がある人々にとっては、この種のものを不要にする言語機能が組み込まれています。
function countArgs (...allArgs) {
return allArgs.length;
}
function logArgs (...allArgs) {
return allArgs.forEach(arg => console.log(arg));
}
function extend (subject, ...others) { /* return ... */ }
var nodeArray = [ ...nodeList1, ...nodeList2 ];
超きれいで、とても便利です。
を調べてみてください。
休む
そして
拡散
BabelJSのサイトで試してみてください。技術的に問題なければ、Babelとビルドステップで本番環境で使用してください。
非配列から配列への変換を使用できない正当な理由はありません... ...ただ、何もしないことでコードを混乱させないようにしてください。 しかし のみで、同じ醜い行をどこにでも貼り付けるような、あなたのコードを混乱させるようなことはしないでください。
関連
-
vueにおけるv-forループオブジェクトのプロパティ
-
[解決済み】Node.jsで "Cannot find module "エラーを解決するには?
-
[解決済み] JavaScriptで "use strict "は何をするのか、その根拠は?
-
[解決済み] JavaScriptで文字列が部分文字列を含むかどうかを確認する方法は?
-
[解決済み] あるJavaScriptファイルを他のJavaScriptファイルにインクルードするにはどうすればよいですか?
-
[解決済み] JavaScriptでオブジェクトをディープクローンする最も効率的な方法は何ですか?
-
[解決済み] JavaScript で配列に値が含まれているかどうかを確認するにはどうすればよいですか?
-
[解決済み] とは何ですか! (not not)演算子とは何ですか?
-
[解決済み】PHPの'foreach'は実際どのように動作するのですか?
-
[解決済み】オブジェクトからプロパティを削除する(JavaScript)
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Vueがechartsのtooltipにクリックイベントを追加するケーススタディ
-
vueはopenlayersを使用してスカイマップとガオードマップをロードする
-
vue+webrtc(Tencent cloud)ライブ機能の実践を実現するために
-
[解決済み] Error : 未定義のプロパティ 'map' を読み取ることができません。
-
[解決済み] 配列の結合時に未定義のプロパティ 'push' を読み込むことができない
-
[解決済み】ExpressJS - throw er Unhandled errorイベント
-
[解決済み】ExpressJS : res.redirect()が期待通りに動かない?
-
[解決済み】 env: node: macにそのようなファイルやディレクトリはありません
-
[解決済み】 Uncaught TypeError : undefined のプロパティ 'replace' を読み取れない In Grid
-
JavaScriptのgetElementById、getElementsByTagNam、getElementsByClassNameの違いと使い方