auto semicolon insertion 自动分号补齐的坑
今天发现js自动分号补齐的坑,来看如下两段代码:
function Hello(){
return
{
name: ’JavaScript’
};
} alert(Hello()); //输出undefined
function Hello(){
return{
name: ’JavaScript’
};
} alert(Hello()); //输出 [object Object]
略看代码,差不多,但是输出却不一样。仔细看看第一段代码return后面多了个换行。我们平时写后端代码也经常有会这样换行后花括号左对齐的写法。但是在js这里这样写却有不同的输出。这种机制叫分号自动补齐机制( auto semicolon insertion,简称ASI )。
知乎上有大神关于这个机制的解释:
在ASI的机制中有一类语句叫做restricted productions(不知道中文叫啥)。简单来说,就是组成这类语句的两个token当中不允许出现换行符 \n。如果在第一个token后面遇到了换行符,则判断语句结束,插入分号。restricted productions包括:
- return xxx (xxx是要返回的对象)
- throw xxx(xxx是要抛出的错误对象)
- break / continue xxx(xxx是循环的标签)
- 作为后缀的 ++ / --
其中前几个关键词还是挺容易记的,最后一条的原因是需要区分以下情况:
a
++
b
因为++/--既可以作为前缀又可以作为后缀,在这样的情况下作为后缀解析会遇上换行符,所以只能作为b的前缀,自动插入分号后变成:
a; ++b;
回到原题,Douglas Crockford认为 { 应该写在行尾,是为了避免换行符导致return直接返回undefined。
篇外:关于分号 ------------------------------------------------------------------------------------------------
很多人觉得ASI坑太多了所以提倡永远手动加分号,这样就不用费心去研究ASI的规则了。但事实上,即使永远手动加分号,你依然会被restricted productions这条规则坑,因为它是在你不想要分号的地方给你插入分号。所以不管你喜不喜欢分号,都最好花点时间好好了解一下ASI的规则。而一旦你知道了ASI所有的坑,不写分号其实是很简单的。
ASI真正需要注意的坑只有两个,restricted productions是其一,另一个就是当下一行开头是 ( [ / 这三个字符之一的时候:
a = b
(function () { ... }())
会被解析成
a = b(function () {...}());
换言之,( ) 会被看做是在调用函数b。同理,[ ] 会被看做是在获取b的属性,而被斜杠坑的情况则要求更苛刻一些:
a = b
/Error/i.test(str) && doSomething()
第二行的写法本身比较少见,但也不是不可能。结果会被解析成:
a = b / Error / i.test(str) && doSomething();
斜杠被解析成了除号!
要躲开这个坑,其实真的挺简单,只要尽量别用这三个字符作为一行开头就行了。事实上遇到比较多的也只有括号开头。真的避不开的话,可以在行头手动加个分号:
a = b
;(function () { ... }())
额外的一点是在for循环声明里面的分号是永远不能省的,ASI不会在for循环声明中插分号,但一般正常人不会把for的声明分三行写吧...
每次我看到 “javascript分号坑很多,所以应该永远加分号” 这样的说法总是有些不屑的,因为永远加分号并不是避免错误的办法,搞懂ASI是怎么回事才是。只要理解了这里说的两个坑,javascript里99%的分号都是不必要的。
auto semicolon insertion 自动分号补齐的坑的更多相关文章
- 【微收藏】来自Twitter的自动文字补齐jQuery插件 - Typeahead.js
没图没逼格 事发有因 该插件可以结合本地数据进行一些操作.推荐关注一下H5的几种数据存储的方式(localstorage与sessionstorage.IndexedDB.离线缓存manifest文件 ...
- jQuery实现Twitter的自动文字补齐特效
上图效果可以使用jQuery插件Typeahead.js来实现,这款jQuery插件来自于Twitter的一个新的项目,支持远程和本地的数据集.比较有特色的地方在于你可以将数据集使用本地存储(loca ...
- CocoaPods 导入第三方库头文件自动补齐
使用了一段时间CocoaPods来管理Objective-c的类库,方便了不少.但是有一个小问题,当我在xcode输入import关键字的时候,没有自动联想补齐代码的功能,需要手工敲全了文件名,难以适 ...
- CocoaPods导入第三方库头文件自动补齐
使用了一段时间CocoaPods来管理Objective-c的类库,方便了不少.但是有一个小问题,当我在xcode输入import关键字的时候,没有自动联想补齐代码的功能,需要手工敲全了文件名,难以适 ...
- GBin1插件推荐之马可波罗(Marco Polo),jQuery的自动补齐插件 - Autocomplete Plugin
让我们Google一下"jQuery autocomplete plugin"(jquery自动补齐插件).在过去的4年中,我已经Google了很多次这个组合了.然而结果并没有变化 ...
- Eclipse -- 自动补齐设置和其他用法
1:自动补齐设置:最简单的修改方式是:Windows——>Preferences——>Java-->Editor-->Content Asist,在Auto activatio ...
- js获取系统时间时自动补齐日期带零
最近在开发中发现有日期不规范的问题,正常规则应该是yy-mm-dd,而在输出时候却变成yy-mm-d,这是js的date()方法在作怪 解决思路是若在10号前,则自动给它补齐一个0,下面给出解决方法, ...
- 为Debian/Ubuntu的apt-get install添加自动补齐/完成功能
Debian/Ubuntu的apt-get太常用了,不过偶尔可能也会碰到不太熟悉,想不起来的包的名称,除了去debian packages去查找,另外的方法就是给Debian/Ubuntu添加自动补齐 ...
- jquery.autocomplete自动补齐和自定义格式
1.简单的下拉自动补齐,可以使用本地或远程数据源 <input name="autoTag" id="autoTag" /> var source ...
随机推荐
- VBA注释临时
Sub shishi() '按ABCDE为多选题定义答案; 'A.沙利度胺 B.异烟肼 C.利福平 'd.氯法齐明 E.氨苯砜 '46.各型麻风病的首选药物为(D) 'A.沙利度胺 B.异烟肼 C.利 ...
- bzoj 1414: [ZJOI2009]对称的正方形
Description Orez很喜欢搜集一些神秘的数据,并经常把它们排成一个矩阵进行研究.最近,Orez又得到了一些数据,并已经把它们排成了一个n行m列的矩阵.通过观察,Orez发现这些数据蕴涵了一 ...
- Jmeter 指令记录
${__machineIP()} 获取当前本地IP地址(后面发现其实这个是在函数助手里面可以选择的)
- JSON: JSON 用法
ylbtech-JSON: JSON 用法 1. JSON Object creation in JavaScript返回顶部 1. <!DOCTYPE html> <html> ...
- 学习笔记之Elasticsearch
Elasticsearch: RESTful, Distributed Search & Analytics | Elastic https://www.elastic.co/products ...
- linux 下安装doker centeros6.5
通过 cat /proc/version .uname [root@192.168.1.1 ~]# cat /proc/version Linux version 2.6.32-279.el6.x86 ...
- 廖雪峰Java1-2程序基础-7布尔运算符
布尔运算符 关系运算符:>, >=, <, <=, ==,!= 与运算 && 或运算 | 非运算 ! int n = 5; boolean t = n > ...
- 学习MongoDB 六: MongoDB查询(游标操作、游标信息)(三)
一.简介 db.collection.find()可以实现根据条件查询和指定使用投影运算符返回的字段省略此参数返回匹配文档中的所有字段.并返回到匹配文档的游标,可以随意修改查询限制.跳跃.和排序顺序的 ...
- Jquery学习(二)
滚轮事件与函数节流 jquery.mousewheel插件使用 jquery中没有鼠标滚轮事件,原生js中的鼠标滚轮事件不兼容,可以使用jquery的滚轮事件插件jquery.mousewheel.j ...
- python super()函数详解
引言: 在类的多继承使用场景中,重写父类的方法时,可能会考虑到需要重新调用父类的方法,所以super()函数就是比较使用也很必要的解决方法: 文章来源: http://www.cnblogs.com/ ...