TL;DR
- オブジェクト内に入れ子構造の関数が定義されているとき、入れ子関数のthisはグローバルオブジェクトを指す
- アロー関数で入れ子関数を定義すると、関数が定義された段階でthisが確定される
実行環境
JSFiddleのJavaScript + NoLibraryで実行
検証
①入れ子関数(関数式で定義)
let obj = {
func1: function() {
console.log(this);
let func2 = function() {
console.log(this)
let func3 = function() {
console.log(this);
}();
}();
}
}
obj.func1();
> {func1: ƒ}
> Window {window: Window, self: Window, document: document, name: '', location: Location, …}
> Window {window: Window, self: Window, document: document, name: '', location: Location, …}
func1内のthisはobjを指しているが、func2/func3内のthisはwindow(=globalThis)を指している
②入れ子関数(func2/func3をアロー関数で定義)
let obj = {
func1: function() {
console.log(this);
let func2 = (() => {
console.log(this)
let func3 = (() => {
console.log(this);
})();
})();
}
}
obj.func1();
> {func1: ƒ}
> {func1: ƒ}
> {func1: ƒ}
アロー関数を使うと、入れ子構造になってもthisの値が書き換わらず、全てobjを指す。
③入れ子関数(全てアロー関数で定義)
let obj = {
func1: () => {
console.log(this);
let func2 = (() => {
console.log(this)
let func3 = (() => {
console.log(this);
})();
})();
}
}
obj.func1();
> Window {window: Window, self: Window, document: document, name: '', location: Location, …}
> Window {window: Window, self: Window, document: document, name: '', location: Location, …}
> Window {window: Window, self: Window, document: document, name: '', location: Location, …}
アロー関数自体はthisを持たないので、func1がアロー関数の場合はthisがグローバルオブジェクトとなる。