函数中的作用域

所谓函数作用域,就是属于这个函数的全部变量都可以在整个函数的范围内使用及复用。

     function foo(a) {
         var b=a;
         function bar(c){
             var c=b*2;
             console.log(c);
         }
         bar();
     }
     foo(3);
     function foo(a) {
         var b=a;
         function bar(c){
             var c=b*2;
             console.log(c);
         }
         bar();
     }
     bar(2);  //not defined

命名冲突

在同一作用域中,相同的命名会引起冲突。

     function foo() {
         function bar(a){
             i=3;
             console.log(i+a);
         }
         for(var i=0;i<10;i++){
             bar(i);
         }
     }
     foo();

上面的代码将会引起冲突,函数会一直执行下去,行成死循环。

如何避免命名冲突呢?

(1)全局命名空间

一些第三方库通常都是在全局对象中声明一个独特的对象,库的方法和实例都在这个对象中,当我们调用时直接调用这个独特的对象就好了。

     var MyLibrary={
         param1:'param1',
         doSomething:function () {

         },
         doElseThing:function () {

         }
         //.......
     }

(2)模块管理

另一种避免冲突的方法和现在的模块机制很接近,就是从众多模块管理器中挑选一个来使用。使用这些工具,任何库都无需将标识符加入到全局作用域中,而是通过依赖管理器的机制将库的标识符显示地导入到另一个特定的作用域中

立执行函数

将函数包裹在一对括号中,使之成为一个表达式,再在后面加一个括号,使之执行,这样函数就会自执行。这种模式又称IIFE。

自执行函数有两种写法形式,第一种是将整个函数写在括号中,再在括号外面加一对括号:(function(){//do something})();

还有一种是:(function(){//do something}())。

这两种写法功能都相同。

自执行函数传参

     (function(doc){
         var a='按钮';
         doc.getElementById('btn').innerText=a;
     })(document);

块作用域

当我们写for循环时,我们都希望i只在循环的上下文中起到作用,而事实上i会被绑定到他所在的作用域中。比如上面的命名冲突中的例子。

那么如何解决块作用域的问题呢?

(1)使用自执行函数将循环包住,设置私有作用域。

     function foo(a) {
         function bar(a){
             i=3;
             console.log(a+i);
         }
         (function(){
             for(var i=0;i<10;i++){
                 bar(i);
             }
         })();
     }
     foo(3); //3 4 5 6 7 8 9 10 11 12

(2)使用es6中的let
let关键字为其声明的变量隐式地劫持了所在的作用域,上述例子可以改成:

     function foo(a) {
         function bar(a){
             i=3;
             console.log(a+i);
         }
         for(let i=0;i<10;i++){
             bar(i);
         }
     }
     foo(3); //3 4 5 6 7 8 9 10 11 12

(3)es6中const也会创建块级作用域。
const可以创建块级作用域,但是他表示常量。修改const创建的变量的值会报错。

     var foo=true;

     if(foo){
         var a=2;
         const b=3;

         a=3;//正常
         b=4;//错误
     }

     console.log(a);
     console.log(b); //b is not defined

《你不知道的javascript》一、函数作用域和块作用域的更多相关文章

  1. Javascript中的词法作用域、动态作用域、函数作用域和块作用域(四)

    一.js中的词法作用域和动态作用域      词法作用域也就是在词法阶段定义的作用域,也就是说词法作用域在代码书写时就已经确定了.       js中其实只有词法作用域,并没有动态作用域,this的执 ...

  2. 《你不知道的JavaScript》整理(一)——作用域、提升与闭包

    最近在读一本进阶的JavaScript的书<你不知道的JavaScript(上卷)>,里面分析了很多基础性的概念. 可以更全面深入的理解JavaScript深层面的知识点. 一.函数作用域 ...

  3. 你不知道的Javascript(上卷)读书笔记之三 ---- 函数作用域与块作用域

    1. 函数中的作用域 函数作用域的含义是指属于这个函数的全部变量都可以在整个函数范围内使用以及复用 2. 隐藏内部实现 函数经常使用于隐藏”内部实现”,可以把变量和函数包裹在一个函数的作用域中,然后用 ...

  4. 读书笔记-你不知道的JS上-函数作用域与块作用域

    函数作用域 Javascript具有基于函数的作用域,每声明一个函数,都会产生一个对应的作用域. //全局作用域包含f1 function f1(a) { var b = 1; //f1作用域包含a, ...

  5. 《你不知道的JavaScript(上)》笔记——作用域闭包

    当函数可以记住并访问所在的词法作用域时, 就产生了闭包, 即使函数是在当前词法作用域之外执行. function wait(message) { setTimeout( function timer( ...

  6. 《你不知道的JavaScript(上)》笔记——函数作用域和块作用域

    关于函数声明:如果 function 是声明中的第一个词, 那么就是一个函数声明, 否则就是一个函数表达式.例如匿名函数这种形式,函数会被当作函数表达式而不是一个标准的函数声明来处理. (functi ...

  7. 《你不知道的JavaScript(上)》笔记——作用域是什么

    Javascript是一门编译语言,它不是提前编译的, 编译结果也不能在分布式系统中进行移植. 在传统编译语言的流程中, 程序中的一段源代码在执行之前会经历三个步骤, 统称为"编译" ...

  8. ES6 学习笔记之二 块作用域与闭包

    "闭包是函数和声明该函数的词法环境的组合." 这是MDN上对闭包的定义. <JavaScript高级程序设计>中则是这样定义的:闭包是指有权访问另一个函数作用域中的变量 ...

  9. JavaScript词法作用域—你不知道的JavaScript上卷读书笔记(一)

    前段时间在每天往返的地铁上抽空将 <你不知道的JavaScript(上卷)>读了一遍,这本书很多部分写的很是精妙,对于接触前端时间不太久的人来说,就好像是叩开了JavaScript的另一扇 ...

随机推荐

  1. Redis & Python/Django 简单用户登陆

    一.Redis key相关操作: 1.del key [key..] 删除一个或多个key,如果不存在则忽略 2.keys pattern keys模式匹配,符合glob风格通配符,glob风格的通配 ...

  2. C#中判断一个集合是另外一个集合的子集

    有这样的两个集合: string[] bigArr = new string[] { "a", "b", "c" };string[] sm ...

  3. 小米2成功使用google组件的办法(为了coc游戏能登录google账户)

    1) 小米商店里下一个 “谷歌应用下载器”2) 用"谷歌应用下载器"安装相应的服务和应用(跟着提示把所有的服务都更新到最新版本就可以了,第3和第4可以不做)3) 小米商店里下一个 ...

  4. THinkphp开启静态(动态)缓存的用法

    <?php return array( //开启静态缓存 'HTML_CACHE_ON' => true, 'HTML_CACHE_RULES' => array( 'News:in ...

  5. WPF 获取程序路径的一些方法,根据程序路径获取程序集信息

    一.WPF 获取程序路径的一些方法方式一 应用程序域 //获取基目录即当前工作目录 string str_1 = System.AppDomain.CurrentDomain.BaseDirector ...

  6. 告诉你吧,一套皮肤在winform与wpf开发模式下实现的界面效果同样精彩,winform界面和wpf界面。

    一.同一资源: 二.先上软件界面: (1)wpf界面: 在wpf中实现这样类似web风格的软件界面就不用我多说了,在wpf实现这样的风格是很简单的,完全像网页设计一样的. (2)winform界面 在 ...

  7. script标签块的独立性与共享性

    块间独立,变量与方法共享 每个script块之间不会相互影响,某个script块出错,不会影响其它块的运行 块之间定义的非局部变量和方法可以共享,(其实只是共享了全局变量和方法) <script ...

  8. HTML5新特性之移动设备API

    为了更好地为移动设备服务,HTML5推出了一系列针对移动设备的API. 1.Geolocation API Geolocation接口用于获取用户的地理位置.它使用的方法基于GPS或者其他机制(比如I ...

  9. JS - Cookie: getCookie, setCookie

    JS function for Cookie 如果cookie未设置,判断时与空字符串‘’比较: function setCookie(cname, cvalue, exdays) { var d = ...

  10. Copy15G的初始容量,注册就再送5G,邀请注册的人也送5G

    Copy15G的初始容量,注册就再送5G,邀请注册的人也送5G,可谓是史上最隆重最给力的容量赠送活动~~~https://copy.com?r=kFpfsZ