JS匿名自执行函数(IIFE)

    JS自执行函数又称为IIFE,在我们开发过程中会使用到大量的自执行函数。

IIFE写法:

    使用建议:在使用只执行函数前面加上 “ ; ”,避免压缩或者打包时变为函数。

    首先我们要了解一般情况下什么是函数声明语句,什么是函数表达式语句,以便于接下来的实验。

    辨别方法:以“function”开头的有名称的函数是函数声明语句。

function a();//函数声明语句

var a = function();//函数表达式语句

    下面我们在分析一道面试题:

var a = function(){}

var b = function(){}

console.log(a()+b());//输出结果是NaN

因为解释器会把前面的a()认为是一个语句块的结束,后面的‘+’一元运算符有把后面b()转换为数字这么一个功能,所以得到的结果是NaN。

因此我们在做自执行函数的时候,要把函数的声明变为函数表达式,这样就不会影响输出的结果了。

方法1:

(function(){

})();

方法2:

(function(){

}() );

方法3(通过操作符):但是这种方法仍然会占用命名空间,所以不建议使用。

var a = function (){

console.log(2)

}()

方法4(通过操作符)与或操作符:

false || function (){

console.log(2)

}()

true && function (){

console.log(2)

}()

0 , function (){

console.log(2)

}()

注:通过操作符实现自执行函数一般使用在打包工具里面,比如webpack打包后会经常看到 ” 0,functtion(){}()“

方法5:(一元运算符)一元运算符仍然可以将函数声明转换为函数表达式,在bootstrap框架中常用。

! function (){

console.log(2)

}()

-function (){

console.log(2)

}()

+function (){

console.log(2)

}()

方法6:new一个匿名函数,后面可省略括号。(不建议使用,会产生争议)

new function (){

console.log(2)

};//在不传参的情况下使用new也可以自执行,可以去掉小括号,不常用。


以上方法性能比较:

除了一元运算符的时候性能偏低,因为要进行一次数字类型的转换,其他的都可以。


应用:

我们要了解,为什么使用自执行函数,确切的说是自执行函数的优点以及缺点:

        1.避免作用域命名污染

        2.提升性能(减少了对作用域的查找)

        3.避免全局命名冲突

                比如jq里面暴露给全局作用域$和query两个变量,为了解决这个问题,我们可以将window.jq作为一个实参传递给一个立即执行的匿名函数。这样的话,我们再次命名$或者query就不会有冲突了。

        4.有利于代码压缩(可以用简单字符串代替)

        5.保存闭包状态

        6.颠倒代码执行顺序

(function(){})(bb())

console.log(12)

function bb(){

        console.log(22)

};//打印顺序是22,12

这就叫做UMD通用模块规范,在实际开发过程中被广泛应用。

        7.模仿块级作用域

    作用域的内部可以访问到外部,外部不可以访问到内部,js作用域的缺陷就是没有块级作用域。

    比如:

            for (var i = 0; i <6; i++) {

            }

            console.log(i);//打印出来的是6,在for循环外面仍然可以访问到变量i。

三个特殊的语句可以欺骗语法分析:


        evel(); //内部存放js代码可被执行

        with(object instance)   {           //代码块   }  ; // with 语句可以方便地用来引用某个特定对象中已有的属性,但是不能用来给对象添加属性。要给对象创建新的属性,必须明确地引用该对象。

        try {   // 此处是可能产生例外的语句   } catch(error) {  // 此处是负责例外处理的语句   } finally {   // 此处是出口语句   }


所以在ES3下,严格来说js是没有块级作用域的,但是以上三种方法可以实现块级作用域的效果。

常用的有try catch,把要声明的变量放在try里面,然后当一个错误抛出,让cath接住使用。缺点:1.多个块级作用域需要多个嵌套;2.性能问题。

匿名自执行函数只能模拟块级作用域,并非真正的作用域。

   let定义的作用域是块级作用域,但不要轻易使用,针对开发场景来选择。

        8.填坑(加载第三方插件时候的一些问题)

                比如有个人写了这样一段代码:undefined=true,再早之前undefined是可以被赋值的,所以这段代码不会报错,但是这样会致使你下面的一些判断出错

                这时候如果使用匿名自执行函数就可以解决:

(function(undefined){

        console.log(undefined)

}())

了解他的优点之后我们才可以在正确的场景使用IIFE。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,271评论 5 466
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,725评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,252评论 0 328
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,634评论 1 270
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,549评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 47,985评论 1 275
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,471评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,128评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,257评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,233评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,235评论 1 328
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,940评论 3 316
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,528评论 3 302
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,623评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,858评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,245评论 2 344
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,790评论 2 339

推荐阅读更多精彩内容

  • 第2章 基本语法 2.1 概述 基本句法和变量 语句 JavaScript程序的执行单位为行(line),也就是一...
    悟名先生阅读 4,102评论 0 13
  • 函数声明和函数表达式有什么区别 (*)解析器会率先读取函数声明,并使其在执行任何代码之前可以访问;函数表达式则必须...
    coolheadedY阅读 382评论 0 1
  • 工厂模式类似于现实生活中的工厂可以产生大量相似的商品,去做同样的事情,实现同样的效果;这时候需要使用工厂模式。简单...
    舟渔行舟阅读 7,709评论 2 17
  • 早安亲爱的小伙伴!貌似最近更多在分享我走过的地方、做过的事情、听过的故事,根据小伙伴的回应和简书后台阅读量...
    黄疍疍阅读 350评论 1 1
  • 无论怎样挣扎 或者多么顺畅 生命总是在不知不觉间往前流逝 渐渐 曾经的激情变平淡 曾经的执着变平常 曾经的骄傲变平...
    梁木子阅读 195评论 1 1