[笔记][JavaScript]关于即刻执行函式(immediately invo....IIFE)的用法

嗨啊啊啊,首先我要先道歉一下,感觉我很多观念都还没打稳,所以打文章的时候并没有讲解的很清楚,只是想说如果试着去理解,并且打出来和大家分享应该会得到更厉害的大大的建议,当然也是真的有啦!但总觉得如果是这样有点不太好意思,虽然把他归类成笔记,但是既然文章出来了,也是一种技术分享,就觉得应该要更认真的去做好这件事情才行。

另外我也在板上另一个大大fysh711426的文章[Google Code Jam] 2018 资格赛中答应说也要试着来解一下问题,关于这个我原本想说用JavaScript来处理掉,但是现在还没有去处理到这部分,哦怎么觉得从客户那欠东西欠到这里了http://img2.58codes.com/2024/emoticon16.gif,不过相信我,我一定会找时间把它处理掉的,如果板上其他大大有兴趣也可以去看一下问题在这里!啊啊啊现在先不要点进去,这篇文章的主题都还没开始,那题外话就不再多说,以下开始!

关于即刻执行函数(immediately invoked function expression),这个不管是中文或是英文都很长,所以大家都简称IIFE,他的意思就如同字面,就是撰写完函式内容后,直接呼叫执行该函数,以下例子:

//一个一般的函式会是以下这样var funcA = function(){    console.log('hello!');};//去执行他funcA();  //会在console中印出'hello!'//而IIFE看起来会是以下这样(function funcB(){ //IIFE的开头    console.log('hello!') //函式内执行的内容}()); //IIFE的结尾//不需要特别去执行就会直接在console中印出hello!funcB();  //但是当我们去做呼叫时会出现「funcB is not defined」的错误,因为在IIFE开头的括号是代表这段程式码是作为一个述句执行里面的运算式,并不是以function去宣告函式,所以他也不会被存在全域变数中,也就不可能呼叫的到了。

接下来继续改写IIFE的内容,IIFE接在函式后右大括号的两个小括号会让函式即刻被执行,也就是说他是靠那个小括号去呼叫的,所以我们可以利用他去加入参数:

//IIFE可以是匿名函式(就是不帮函式取名字),因为他马上就会执行了,之后也不需要再呼叫他,所以有没有名字都无所谓。(function(str){   //我们在这里加入str用来装执行时传入的参数。    console.log(str);}('hello'));   //我们把字串'hello'传入IIFE中//不需要执行便会直接在console中印出hello

再来我们看一下IIFE的奇行种http://img2.58codes.com/2024/emoticon37.gif,上面第一个例子的最后有提到说,开头的括号是作为一个述句宣告,为了能让里面的程式码变成运算式执行,所以说其实只要能够让该匿名函式变成运算式都能够当成IIFE来使用!例如以下:

//function和上面例子一样,不同的是把原本包着他的括号拿掉,并在前面放一个!运算子!function(str){       console.log(str);}('hello'); //登愣!会发现他还是会在console中印出hello,但是他会回传个结果true,因为!运算子会回传boolean的值,而该函式没有return东西也就是undefined,但是!是Not运算子,所以会把结果从undefined的false转成ture回传,好,这是有点长的题外话,那我们继续看下去。//如果他本身就是在运算子的环境中,甚至不需要再把他变成运算子,例如:var funcA =     function(str){           console.log(str);    }('hello'); //一样会直接在console中印出hello!

好的,那我们讲了那么多IIFE,但是他到底可以用在什么地方呢?大家应该都知道JavaScript的变数範围有分成全域和区域,IIFE就是为了让全域变数的环境不被全域变数汙染,和在区域中,建立一个新的环境,避免在同个区域内共用同个变数。

让我们看看以下在全域环境使用的例子:

//先建立几个简单的函式function writeStr(str){    console.log(str);};function setValue(){    return 'A'};//在全域中使用var strA = setValue();  //设定strA的值writeStr(strA);  //把strA的值交给函式writeStr印出到consolestrA; //会回传'A'因为他已经被存在window,也就是全域环境中了//虽然以上这么做是没问题的,但是全域环境会增加一个strA,这对于依赖全域环境做执行的JavaScript容易出现一些问题,所以我们应该要避免汙染到全域变数,如下://建立IIFE(function(){    var strB = setValue();   //在IIFE中的匿名函式中宣告该变数,他的範围就只会在这个IIFE中,不会汙染到全域环境。    writeStr(strB);  //一样把strA丢到函式writeStr印到console上}());strB; //会出现strB is not defined的错误,全域变数没被汙染

最后是在区域中使用的例子:

//建立一个一般的函式,并观察temp在各个地方的变化function funcA(str){    var temp = '';    console.log('(1):' + temp);    if(str !== ''){        var temp = str;        console.log('(2):' + temp);    }    console.log('(3):' + temp);};funcA('hello');  //执行后会在console上印出://(1):''//(2):hello//(3):hello//会发现在if内宣告的同名变数temp会在if中设定新的值后,会连整个函式funcA原本的temp值都改变了。//接着在函式内使用IIFE,再观察temp的变化function funcB(str){    var temp = '';    console.log('(1):' + temp);    if(str !== ''){        (function(){        var temp = str;        console.log('(2):' + temp);}());    }    console.log('(3):' + temp);};funcB('hello');//执行后会在console上印出://(1):''//(2):hello//(3):''//可以看到temp这个变数在IIFE中被改变的内容并不会遗留到IIFE外的任何地方,这样就可以避免在同个环境执行时,共用同个变数名称会影响到原本的内容。

以上是对IIFE的一些说明和应用,如果有说明错误或不明白的地方,麻烦再留言告知我,我会尽速改正!!谢谢大家!!


关于作者: 网站小编

码农网专注IT技术教程资源分享平台,学习资源下载网站,58码农网包含计算机技术、网站程序源码下载、编程技术论坛、互联网资源下载等产品服务,提供原创、优质、完整内容的专业码农交流分享平台。

热门文章