「矢印関数」と「関数」は同等/交換可能ですか?

575
Felix Kling 2015-12-19 07:58.

ES2015の矢印関数は、より簡潔な構文を提供します。

  • すべての関数宣言/式を矢印関数に置き換えることはできますか?
  • 何に注意する必要がありますか?

例:

コンストラクター関数

function User(name) {
  this.name = name;
}

// vs

const User = name => {
  this.name = name;
};

プロトタイプメソッド

User.prototype.getName = function() {
  return this.name;
};

// vs

User.prototype.getName = () => this.name;

オブジェクト(リテラル)メソッド

const obj = {
  getName: function() {
    // ...
  }
};

// vs

const obj = {
  getName: () => {
    // ...
  }
};

コールバック

setTimeout(function() {
  // ...
}, 500);

// vs

setTimeout(() => {
  // ...
}, 500);

可変個引数関数

function sum() {
  let args = [].slice.call(arguments);
  // ...
}

// vs
const sum = (...args) => {
  // ...
};

3 answers

817
Felix Kling 2015-12-19 07:58.

tl; dr: いいえ!矢印関数と関数宣言/式は同等ではなく、盲目的に置き換えることはできません。
置き換えたい関数がを使用せthisargumentsで呼び出されない場合は、newはい。


よくあることですが、状況によって異なります。矢印関数の動作は関数宣言/式とは異なるため、最初に違いを見てみましょう。

1.語彙thisarguments

アロー機能は、独自のを持っていないthisか、arguments結合します。代わりに、これらの識別子は、他の変数と同様に字句スコープで解決されます。ことを意味する矢印関数内、ことthisargumentsの値を参照thisし、arguments矢印機能がされている環境で定義された(すなわち、「外部」矢印関数)で:

// Example using a function expression
function createObject() {
  console.log('Inside `createObject`:', this.foo);
  return {
    foo: 42,
    bar: function() {
      console.log('Inside `bar`:', this.foo);
    },
  };
}

createObject.call({foo: 21}).bar(); // override `this` inside createObject

// Example using a arrow function
function createObject() {
  console.log('Inside `createObject`:', this.foo);
  return {
    foo: 42,
    bar: () => console.log('Inside `bar`:', this.foo),
  };
}

createObject.call({foo: 21}).bar(); // override `this` inside createObject

関数式の場合、thisは、内で作成されたオブジェクトを参照しますcreateObject。矢印関数場合、thisを意味するthiscreateObject自体。

これによりthis、現在の環境にアクセスする必要がある場合に矢印関数が役立ちます。

// currently common pattern
var that = this;
getData(function(data) {
  that.data = data;
});

// better alternative with arrow functions
getData(data => {
  this.data = data;
});

これは、またはで矢印関数を設定できないことも意味することに注意しくださいthis.bind.call

あなたがあまり精通していない場合はthis、読むことを検討してください

2.矢印関数はで呼び出すことはできません new

ある関数間ES2015区別呼んでいることや機能の構築が可能。関数が構築可能である場合、それはnew、すなわちで呼び出すことができます new User()。関数が呼び出し可能である場合、それはなしでnew呼び出すことができます(つまり、通常の関数呼び出し)。

関数宣言/式を介して作成された関数は、構築可能であり、呼び出し可能です。
矢印関数(およびメソッド)は呼び出し可能です。 classコンストラクターは構築可能です。

呼び出し不可能な関数を呼び出そうとしたり、構築不可能な関数を構築しようとすると、ランタイムエラーが発生します。


これを知って、私たちは次のように述べることができます。

交換可能:

  • thisまたはを使用しない関数arguments
  • で使用される関数 .bind(this)

交換不可

  • コンストラクター関数
  • プロトタイプに追加された関数/メソッド(通常は使用するためthis
  • 可変個引数関数(使用する場合arguments(以下を参照))

あなたの例を使ってこれを詳しく見てみましょう:

コンストラクター関数

矢印関数はnew。で呼び出すことができないため、これは機能しません。関数宣言/式を使い続けるか、を使用してくださいclass

プロトタイプメソッド

プロトタイプメソッドは通常this、インスタンスへのアクセスに使用するため、ほとんどの場合そうではありません。を使用しない場合はthis、交換できます。ただし、主に簡潔な構文を重視する場合classは、簡潔なメソッド構文を使用してください。

class User {
  constructor(name) {
    this.name = name;
  }
  
  getName() {
    return this.name;
  }
}

オブジェクトメソッド

オブジェクトリテラルのメソッドについても同様です。メソッドがを介してオブジェクト自体を参照する場合は、this関数式を引き続き使用するか、新しいメソッド構文を使用します。

const obj = {
  getName() {
    // ...
  },
};

コールバック

場合によります。アウターをエイリアシングしている場合、thisまたは使用している場合は、必ず交換する必要があります.bind(this)

// old
setTimeout(function() {
  // ...
}.bind(this), 500);

// new
setTimeout(() => {
  // ...
}, 500);

ただしthis、イベントハンドラー、特にjQueryの場合によくあるように、コールバックを呼び出すコードが明示的に特定の値に設定され、コールバックがthis(またはarguments)を使用する場合、矢印関数使用できません

可変個引数関数

矢印関数には独自のものargumentsがないため、単純に矢印関数に置き換えることはできません。ただし、ES2015では、argumentsrestパラメーターを使用する代わりの方法が導入されています

// old
function sum() {
  let args = [].slice.call(arguments);
  // ...
}

// new
const sum = (...args) => {
  // ...
};

関連する質問:

その他のリソース:

17
Ashutosh 2020-01-10 10:22.

矢印関数=>これまでで最高のES6機能。これらはES6への非常に強力な追加機能であり、私は常に使用しています。

待ってください。コード内のどこでも矢印関数を使用することはできません。矢印関数が使用できない場合など、すべての場合にthis機能するわけではありません。間違いなく、矢印関数はコードを単純化するための優れた追加機能です。

ただし、動的コンテキストが必要な場合は矢印関数を使用できません。メソッドの定義、コンストラクターを使用したオブジェクトの作成、イベントの処理時にこれからターゲットを取得します。

次の理由により、矢印関数は使用しないでください。

  1. 彼らは持っていない this

    「字句スコープ」を使用して、「this」の値がどうあるべきかを判断します。簡単な単語の字句スコープではthis、関数の本体の内側から「」を使用します。

  2. 彼らは持っていない arguments

    矢印関数にはargumentsオブジェクトがありません。ただし、RESTパラメーターを使用して同じ機能を実現できます。

    let sum = (...args) => args.reduce((x, y) => x + y, 0) sum(3, 3, 1) // output - 7 `

  3. と一緒に使用することはできません new

    矢印関数にはプロトタイププロパティがないため、コンストラクターにすることはできません。

矢印機能を使用する場合と使用しない場合:

  1. これにアクセスできないため、オブジェクトリテラルのプロパティとして関数を追加するために使用しないでください。
  2. 関数式はオブジェクトメソッドに最適です。アロー機能は次のようにコールバックや方法のために最適ですmapreduceまたはforEach
  3. 名前で呼び出す関数には関数宣言を使用します(関数が引き上げられているため)。
  4. コールバックには矢印関数を使用します(それらはより簡潔になる傾向があるため)。
2
toddmo 2020-05-16 15:56.

で矢印関数を使用するためfunction.prototype.callに、オブジェクトのプロトタイプでヘルパー関数を作成しました。

  // Using
  // @func = function() {use this here} or This => {use This here}
  using(func) {
    return func.call(this, this);
  }

使用法

  var obj = {f:3, a:2}
  .using(This => This.f + This.a) // 5

編集

ヘルパーは必要ありません。あなたができること:

var obj = {f:3, a:2}
(This => This.f + This.a).call(undefined, obj); // 5

Related questions

MORE COOL STUFF

ケイト・ブランシェットは3日間一緒に夫と一緒に寝て、25年経ってもまだ夫と結婚しています

ケイト・ブランシェットは3日間一緒に夫と一緒に寝て、25年経ってもまだ夫と結婚しています

ケイト・ブランシェットは、夫に会ったとき、典型的な交際のアドバイスに逆らいました。

マイケルシーンが非営利の俳優である理由

マイケルシーンが非営利の俳優である理由

マイケルシーンは非営利の俳優ですが、それは正確にはどういう意味ですか?

ホールマークスターのコリンエッグレスフィールドがRomaDramaLiveでスリル満点のファンと出会う![エクスクルーシブ]

ホールマークスターのコリンエッグレスフィールドがRomaDramaLiveでスリル満点のファンと出会う![エクスクルーシブ]

特徴的なスターのコリン・エッグレスフィールドは、RomaDrama Liveでのスリル満点のファンとの出会いについて料理しました!加えて、大会での彼のINSPIREプログラム。

「たどりつけば」をオンラインでストリーミングできない理由

「たどりつけば」をオンラインでストリーミングできない理由

ノーザンエクスポージャーが90年代の最も人気のある番組の1つになった理由を確認するには、Blu-rayまたはDVDプレーヤーをほこりで払う必要があります。

バイオニック読書はあなたをより速く読むことができますか?

バイオニック読書はあなたをより速く読むことができますか?

BionicReadingアプリの人気が爆発的に高まっています。しかし、それは本当にあなたを速読術にすることができますか?

ドミニカのボイリング湖:アクセスは簡単ではありませんが、ハイキングする価値があります

ドミニカのボイリング湖:アクセスは簡単ではありませんが、ハイキングする価値があります

ドミニカのボイリング湖は、世界で2番目に大きいボイリング湖です。そこにたどり着くまでのトレッキングは大変で長いですが、努力する価値は十分にあります。

私たちの水をきれいに保つのを助けるためにあなたの髪を寄付してください

私たちの水をきれいに保つのを助けるためにあなたの髪を寄付してください

サロンからのヘアトリミングや個人的な寄付は、油流出を吸収して環境を保護するのに役立つマットとして再利用できます。

ホワイトハウスの最も記憶に残る結婚式を見てください

ホワイトハウスの最も記憶に残る結婚式を見てください

過去200年以上の間にホワイトハウスで結婚したのはほんの数人です。彼らは誰でしたか、そしてそこで結婚式を獲得するために何が必要ですか?

ねえNFL、ジョーバロウとカイラーマレーは女性の権利をサポートするために少しの助けを使うことができます

ねえNFL、ジョーバロウとカイラーマレーは女性の権利をサポートするために少しの助けを使うことができます

ジョー・バロウロー対ウェイド事件の転覆に対応するNFLは、言葉を言わないことで、腹立たしいが予測可能なPRの結果でした。

別の日、別のヒンジのないLIV記者会見

別の日、別のヒンジのないLIV記者会見

(lから)パット・ペレス、ブルックス・ケプカ、パトリック・リードサウジアラビアのLIVゴルフリーグのさらに別の信じられないほどの記者会見で、スポーツのファンはブルックス・ケプカからでたらめな吐き気と質問回避の驚異的なマスタークラスを受けました。パトリックリード、ブライソンデシャンボー、パットペレス、最近のPGAツアーの脱北者。

ミズ・マーベルの家族の帰郷は悪役よりも激しく打撃を与える

ミズ・マーベルの家族の帰郷は悪役よりも激しく打撃を与える

レッドダガーとマーベルさんがチームを組んでいます。

6億7500万ドルのビットコインローンのデフォルト後にすべての資産を清算するように命じられたスリーアローズキャピタル

6億7500万ドルのビットコインローンのデフォルト後にすべての資産を清算するように命じられたスリーアローズキャピタル

暗号業界最大の沈没船の1つであるスリーアローズキャピタルは、ついにその悲惨さから解放されています。火曜日に、不良債権ヘッジファンドは、債権者からの返済を要求する訴訟の高まりに応えて、バージンアイランド裁判所によって清算を命じられました彼らが3ACに行ったローン。

Zendaya Wishes Boyfriend Tom Holland Happy Birthday with Cuddly Photo: He 'Makes Me the Happiest'

Zendaya Wishes Boyfriend Tom Holland Happy Birthday with Cuddly Photo: He 'Makes Me the Happiest'

Zendaya shared a sweet photo in honor of boyfriend Tom Holland's 26th birthday Wednesday

小さな女性:脳卒中を患った後に病院から解放されたアトランタのジューシーな赤ちゃん:「まだ癒し」

小さな女性:脳卒中を患った後に病院から解放されたアトランタのジューシーな赤ちゃん:「まだ癒し」

シーレン「Ms.JuicyBaby」ピアソンは、先月脳卒中で入院した後、「もう一度たくさんのことをする方法を学ばなければならない」ため、言語療法を受けていることを明らかにしました。

エマストーンは彼女のクリフサイドマリブビーチハウスを420万ドルでリストアップしています—中を見てください!

エマストーンは彼女のクリフサイドマリブビーチハウスを420万ドルでリストアップしています—中を見てください!

オスカー受賞者の世紀半ばの家には、3つのベッドルーム、2つのバス、オーシャンフロントの景色があります。

ジーニー・メイ・ジェンキンスは、母乳育児の経験の中で、彼女は「本当に、本当に落ち込んでいる」と言います

ジーニー・メイ・ジェンキンスは、母乳育児の経験の中で、彼女は「本当に、本当に落ち込んでいる」と言います

ジーニー・メイ・ジェンキンスは、生後4か月の娘、モナコに母乳育児をしていると語った。

Suffragettes Indicam #3: Junho

Suffragettes Indicam #3: Junho

Mais um mês se findando — e metade do ano de 2022 já passou. Sabe o que isso significa? Não, não é hora de verificar se você está cumprindo com suas resoluções de Ano Novo.

多元宇宙—Junø

多元宇宙—Junø

チェーン間アカウントがJunoに登場します。異なるブロックチェーン間でスマートコントラクトの構成可能性と真の相互運用性を提供します。

#brand【ベター・コール・ソール!アメリカのテレビシリーズ「ブレイキング・バッド」に最高のビジネス例が隠されている】・・・ルールクリエイティブ

#brand【ベター・コール・ソール!アメリカのテレビシリーズ「ブレイキング・バッド」に最高のビジネス例が隠されている】・・・ルールクリエイティブ

1.ドラマを見た後、起業する考えはありますか?あなたのビジネスはボトルネックに遭遇しましたか?方向性がなくてわからない場合は、ドラマを追いかけて行くことを心からお勧めします。(?)ブラフではなく、最も完璧なビジネス例を隠すドラマがあります。2.ブレイキング・バッドとその弁護士ドラマ「ブレイキング・バッド」を見た友人たちは、演劇の中で、穏やかな表情で、弁護士のソウル・グッドマンに深く感銘を受けなければなりません。口を開けて、感覚の弱い傭兵の性格を持っています。道徳の面で、サル・グッドマンは無意識のうちに劇に欠かせない役割を果たし、彼自身のシリーズ「絶望的な弁護士」(ベター・コール・ソール)を生み出しました。ウェントウのテキストとビデオは、劇中のソウル・グッドマンのテレビコマーシャルです。製品(サービス)、競争戦略、市場ポジショニング、ブランド名、ターゲット顧客グループ、コミュニケーション軸から広告まで、サル・グッドマンの役割のビジネス設定は、「最低」と見なすことができる超超超超超超完全です。ブランドコミュニケーションのコスト」「変化」のモデル。なぜ?私の分析をご覧ください。3.ソウル・グッドマンの「事業戦略」1.基本情報ブランド名:Saul Goodman製品:法律相談サービス対象顧客:麻薬中毒、飲酒運転、事故など。法律知識の欠如は、一般的に公立弁護士にしか余裕がなく、真面目な弁護士も「特別な法律を持つ消費者」を避けます。恐れてはいけない「​​ニーズ」。コミュニケーションの主軸:この国のすべての男性、女性、子供は有罪判決を受けるまで無実だと思います。地域:アルバカーキ市スローガン:Thrallに電話したほうがいいです!(ベター・コール・ソール)広告:2つの可能性のある犯罪状況をシミュレートします+サウルの主張+サウルのスローガン2をより適切に呼び出します。

メインネットガイド— Arbitrum Odyssey Week 2

メインネットガイド— Arbitrum Odyssey Week 2

最新のアップデートを受け取るために私たちに従ってください。ニュースレター:https://www。

Language