Rumah > Soal Jawab > teks badan
Mengapa pembolehubah n tidak ditetapkan semula?
function f1(){
var n=999;
nAdd=function(){n+=1}
function f2(){
alert(n);
}
return f2;
}
var result=f1();
result(); // 999
nAdd();
result(); // 1000
Terangkan bahawa pembolehubah n ialah pembolehubah global Adakah pembolehubah n dinaikkan kepada pembolehubah global dalam f2?
给我你的怀抱2017-05-18 10:52:47
Oleh kerana js akan mencipta tindanan untuk setiap panggilan fungsi, fungsi dalam fungsi juga boleh mengakses tindanan ini.
Pertama sekali, anda boleh memanggil nAdd
kerana anda tidak menambah var
, yang bersamaan dengan mentakrifkan nAdd
dalam skop global apabila fungsi dipanggil , jika anda menambah var
dan menulis seperti ini, ralat akan dilaporkan. nAdd
,是因为你没加var
,等于是在函数调用时定义了一个全局作用域下的nAdd
,你加上var
再这么写会报错。
你的var result=f1();
调用了函数f1
,也就创建了一个栈,保存了n=999
,并返回了f2
。之后你再怎么调用result()
,其实都是在调用同一个f2
,而这个f2
引用的外部栈,自然还是第一次调用f1
时候创建的那个。同样的nAdd
var result=f1();
anda memanggil fungsi f1
, yang mencipta tindanan, menyimpan n=999
dan Dikembalikan f2
. Tidak kira bagaimana anda memanggil result()
selepas itu, anda sebenarnya memanggil f2
yang sama dan susunan luaran yang dirujuk oleh f2
ini secara semula jadi yang ketiga yang dibuat apabila f1
dipanggil sekali. Walaupun nAdd
yang sama bertindak secara global, ia juga mengakses data dalam tindanan yang sama. Jadi, bukan n dipromosikan kepada pembolehubah global kerana nAdd ialah pembolehubah global, tetapi fungsi yang ditunjukkan oleh nAdd dan penutupan yang anda kembalikan pada dasarnya mengakses data yang sama.
Anda boleh cuba menulis semula sebagai 🎜
function f1(){
var n=999;
nAdd=function(){n+=1}
function f2(){
alert(n);
}
return f2;
}
f1()(); // 调用f1,创建了一个栈,栈内n=999,创建了一个匿名函数,返回了一个闭包。
nAdd(); // 调用了那个匿名函数
f1()(); // 又调用f1,又创建了一个栈,栈内n=999,创建了另一个匿名函数,返回了另一个闭包。
我想大声告诉你2017-05-18 10:52:47
Dalam kod ini, hasilnya sebenarnya ialah fungsi penutupan f2. Ia dijalankan dua kali, kali pertama nilainya ialah 999, kali kedua nilainya ialah 1000. Ini membuktikan bahawa pembolehubah tempatan n dalam fungsi f1 sentiasa disimpan dalam ingatan dan tidak dikosongkan secara automatik selepas f1 dipanggil.
Kenapa ini berlaku? Sebabnya ialah f1 ialah fungsi induk bagi f2, dan f2 diberikan kepada pembolehubah global, yang menyebabkan f2 sentiasa berada dalam ingatan, dan kewujudan f2 bergantung kepada f1, jadi f1 sentiasa dalam ingatan dan tidak akan dipadamkan. selepas panggilan selesai , dikitar semula oleh mekanisme kutipan sampah (kutipan sampah).
Perkara lain yang perlu diberi perhatian dalam kod ini ialah baris "nAdd=function(){n+=1}". Pertama sekali, kata kunci var tidak digunakan sebelum nAdd, jadi nAdd ialah pembolehubah global, bukan pembolehubah setempat. Kedua, nilai nAdd ialah fungsi tanpa nama, dan fungsi tanpa nama ini sendiri juga merupakan penutup, jadi nAdd adalah bersamaan dengan penetap, yang boleh beroperasi pada pembolehubah tempatan di dalam fungsi di luar fungsi.
http://www.ruanyifeng.com/blo...
ringa_lee2017-05-18 10:52:47
Bukan n
被提升为全局变量了,这就是闭包。。。。
是nAdd
是全局变量。nAdd
和result
中涉及的n
都是 var n = 999
那个n
,而没有全局的n
http://zonxin.github.io/post/...
仅有的幸福2017-05-18 10:52:47
var nAdd = ... Jika anda mencuba lagi anda akan tahu mengapa
Jika tiada pengisytiharan var, ia akan dinaikkan pangkat kepada pembolehubah global
Pembolehubah n bukan pembolehubah global Hanya dengan menulisnya seperti ini menghalang ingatan n daripada dilepaskan
给我你的怀抱2017-05-18 10:52:47
Fungsi f2 mempunyai rujukan berterusan kepada pembolehubah tempatan n dalam fungsi f1 Selepas f2 kembali, n tidak akan dikeluarkan, dan nAdd, sebagai fungsi global, sudah tentu boleh beroperasi pada n
.ringa_lee2017-05-18 10:52:47
n masih merupakan pembolehubah tempatan, kerana operasi pembolehubah tempatan n sentiasa dilakukan dalam fungsi f1. nAdd() ialah fungsi global Apabila ia dilaksanakan, n dalam skopnya akan meningkat sebanyak 1
阿神2017-05-18 10:52:47
var result=f1(); Apabila dipanggil, fungsi dalaman f2 dikembalikan dan pembolehubah n fungsi luaran dirujuk Disebabkan oleh mekanisme pengumpulan sampah, apabila f1 selesai. n belum dikitar semula Apabila result() dilaksanakan untuk kali kedua, n menjadi 1000
nTambah pembolehubah global, tiada var ditambah, jadi ia adalah skop global
n ialah pembolehubah setempat
黄舟2017-05-18 10:52:47
var result=f1()
: Fungsi f1 mengembalikan fungsi f2
Berikan fungsi f2 yang dikembalikan kepada pembolehubah global hasil, var result=f1()
:f1函数返回了f2函数
把返回的f2函数赋值给result全局变量,(f2的作用域链保存到result全局变量中)
result()
:调用result(),这就形成闭包:有权访问另外一个函数作用域中的变量
因为在f2中的作用域引用了f1中的n这个局部变量,当f1执行完毕后,垃圾回收机制发现n变量还在被result中引用所以垃圾回收机制不会把n回收释放。
以至于n一直保存在result作用域链中。result的作用域链正常能访问f1中的局部变量n,形成闭包。
nAdd()
:nAdd没有写var所以nAdd是全局变量,在调用nAdd()和result()是一样的都会形成闭包,匿名函数function(){n+=1}的作用域链中有n这个局部变量,所以当nAdd=funtion(){n+=1}时,这个匿名函数的作用域链保存到了全局变量nAdd形成闭包,调用nAdd()作用域链中找到f1局部变量n=999,n+1=1000。
result()
(rantaian skop f2 disimpan dalam hasil global berubah-ubah)
nAdd()
: nAdd tidak menulis var, jadi nAdd ialah pembolehubah global Memanggil nAdd() dan result() adalah sama dan akan membentuk penutupan fungsi tanpa nama(){. n+=1} Terdapat pembolehubah tempatan n dalam rantai skop, jadi apabila nAdd=function(){n+=1}, rantai skop fungsi tanpa nama ini disimpan ke pembolehubah global nAdd untuk membentuk penutupan, yang ditemui dalam rantai skop dengan memanggil nAdd() f1 pembolehubah tempatan n=999, n+1=1000. 🎜🎜
🎜🎜PHP中文网2017-05-18 10:52:47
n bukan pembolehubah global, ia adalah penutupan. Mengapa n berubah? Kerana anda tidak menulis var di hadapan nAdd anda dan ia lalai kepada global, tetapi fungsi anda ditakrifkan dalam penutupan, dan skop dan sebagainya semuanya berada di dalam.