Referensi ke ECMA 5 perlu diklarifikasi.
Saya berasumsi bahwa ini berarti ECMA-262 Edition 5. Perlu dicatat bahwa ECMA-262 (alias ECMAScript atau, kurang akurat, Javascript) adalah bahasa skrip umum yang telah diterapkan di Browser Internet. Dari standar Edisi 5.1:
Langkah-langkah berikut dilakukan ketika kontrol memasuki konteks eksekusi untuk kode fungsi yang terdapat dalam objek fungsi F, pemanggil menyediakan thisArg, dan pemanggil menyediakan argumentsList:
- Jika kode fungsi adalah kode ketat, setel ThisBinding ke thisArg.
- Lain jika thisArg null atau undefined, setel ThisBinding ke objek global.
- Lain jika Type (thisArg) bukan Object, setel ThisBinding ke ToObject (thisArg).
- Lain atur ThisBinding ke thisArg
- ... (bukan tentang "ini")
Istilah "objek global" mengacu pada objek apa pun yang berada di puncak rantai cakupan. Untuk browser ini akan menjadi objek "jendela" tetapi ini adalah pilihan implementasi (Host Skrip Windows memiliki objek global yang tidak terlihat tetapi tidak ada mode ketat sehingga referensi yang tidak memenuhi syarat mengakses propertinya dan tidak ada "diri" global). Selain itu, "mode ketat" harus diaktifkan secara eksplisit jika tidak, mode ini tidak aktif (bagian 14.1 standar). Dengan demikian, "ini" yang tidak ditentukan akan tetap menyelesaikan objek global (jendela) di "ECMA 5" dengan mode ketat tidak aktif.
Jadi jawaban dari pertanyaannya adalah:
"ini" selalu mengacu pada objek yang menjalankan fungsi. Jika fungsi tidak dipanggil oleh objek (yaitu bukan pemanggilan metode) maka "ini" (seperti yang diteruskan ke fungsi) adalah "tidak ditentukan". Namun, jika TIDAK menggunakan mode ketat maka "ini" yang tidak ditentukan disetel ke objek global (aturan 2 di atas).
"diri" tidak memiliki arti sintaksis khusus, ini hanya sebuah pengenal. Browser cenderung mendefinisikan window.self (hanya properti dari objek jendela global) = window. Ini menghasilkan referensi yang tidak memenuhi syarat untuk "self" yang sama dengan "window" KECUALI "self" telah didefinisikan ulang dalam lingkup yang melingkupi (seperti dengan "var self = this;" di atas. Semoga berhasil mendefinisikan kembali "ini".)
Jadi penjelasan lengkap dari contoh diatas adalah:
outer func: this.foo = bar
// "this" refers to the invoking object "myObject"
outer func: self.foo = bar
// "self" resolves to the variable in the local scope which has been set to "this" so it is also "myObject"
inner func: this.foo = undefined
// "this" refers to the invoking object (none) and so is replaced by the global object (strict mode must be off). "window" has no foo property so its "value" is undefined.
inner func: self.foo = bar
// self resolves to the variable in the enclosing scope which is still "myObject"
Variasi yang menarik dari contoh tersebut membuat penutupan dengan mengembalikan referensi ke fungsi bagian dalam.
var myObject = {
foo: "bar",
func: function() {
var self = this;
console.log("outer func: this.foo = " + this.foo);
console.log("outer func: self.foo = " + self.foo);
return function() {
console.log("inner func: this.foo = " + this.foo);
console.log("inner func: self.foo = " + self.foo);
};
}
};
var yourObject = {
foo: "blat",
func: myObject.func() // function call not function object
};
console.log("----");
yourObject.func();
Memproduksi
outer func: this.foo = bar
outer func: self.foo = bar
----
inner func: this.foo = blat
inner func: self.foo = bar
Perhatikan bagaimana fungsi bagian dalam tidak dipanggil sampai dipanggil oleh yourObject. Jadi this.foo sekarang adalah yourObject.foo tetapi self masih menyelesaikan ke variabel dalam lingkup yang melingkupi yang, pada saat objek fungsi bagian dalam dikembalikan, adalah (dan dalam penutupan yang dihasilkan masih) myObject. Jadi, di dalam fungsi bagian dalam, "ini" mengacu pada objek yang memanggil fungsi dalam sedangkan "diri" mengacu pada objek yang disebut fungsi luar untuk membuat referensi ke fungsi dalam.
Untuk meringkas ringkasan ringkasan, "ini" didefinisikan oleh standar bahasa, "diri" didefinisikan oleh siapa pun yang mendefinisikannya (pelaksana runtime atau pemrogram akhir).