JavaScript中:表达式和语句的区别
JavaScript中:表达式和语句的区别
Javascript语言精粹:
表达式是由运算符构成,并运算产生结果的语法结构。
程序是由语句构成,语句则是由“;(分号)”分隔的句子或命令。
如果在表达式后面加上一个“;”分隔符,这就被称为“表达式语句”。它表明“只有表达式,而没有其他语法元素的语句”
原文:http://www.2ality.com/2012/09/expressions-vs-statements.html
本文要讲的是JavaScript中非常重要的两个知识点:表达式(expressions)和语句(statements)之间的区别.
1.语句和表达式
JavaScript中的表达式和语句是有区别的.一个表达式会产生一个值,它可以放在任何需要一个值的地方,比如,作为一个函数调用的参数.下面的每行代码都是一个表达式:
myvar
3 + x
myfunc("a", "b")
语句可以理解成一个行为.循环语句和if语句就是典型的语句.一个程序是由一系列语句组成的.JavaScript中某些需要语句的地方,你可以使用一个表达式来代替.这样的语句称之为表达式语句.但反过来不可以:你不能在一个需要表达式的地方放一个语句.比如,一个if语句不能作为一个函数的参数.
2.其他语法
看看下面这两对类似的语法,搞懂这些后,能够帮助我们更好的理解语句和表达式之间的关系.
2.1 If语句和条件运算符
下面是一个if语句的例子:
var x;
if (y >= 0) {
x = y;
} else {
x = -y;
}
类似if语句功能的表达式叫做条件运算符.上面的语句等价于下面的.
var x = (y >= 0 ? y : -y);
在等于号=和分号;之间的代码就是条件表达式.两边的小括号不是必需的,但我觉得小括号能让条件表达式更易读.
2.2 分号和逗号运算符
在JavaScript中,使用分号可以连接两个语句:
foo(); bar()
要想连接两个表达式,使用的是不常见的逗号运算符:
foo(), bar()
逗号运算符会计算前后两个表达式,然后返回右边表达式的计算结果.例如:
> "a", "b"
'b' > var x = ("a", "b");
> x
'b' > console.log(("a", "b"));
b
3.看似语句的表达式
一些表达式看起来像是语句,这可能会带来一些麻烦.
3.1 对象字面量和语句块
下面是一个对象字面量,也就是一个可以生成一个对象值的表达式.
{
foo: bar(3, 5)
}
不过同时,它也是一个完全合法的语句,这个语句的组成部分有:
- 一个代码块:一个由大括号包围的语句序列.
- 一个标签:你可以在任何语句前面放置一个标签.这里的foo就是一个标签.
- 一条语句:表达式语句bar(3, 5).
你也许会感到震惊,那就是JavaScript居然可以有独立的代码块(常见的代码块是依托于循环或者if语句的).下面的代码演示了这种代码块的作用:你可以给它设置一个标签然后跳出这个代码块.
function test(printTwo) {
printing: {
console.log("One");
if (!printTwo) break printing;
console.log("Two");
}
console.log("Three");
}
> test(false)
One
Three
> test(true)
One
Two
Three
3.2 函数表达式和函数声明
下面的代码是一个函数表达式:
function () { }
你还可以给这个函数表达式起一个名字,将它转变为一个命名(非匿名)的函数表达式:
function foo() { }
这个函数的函数名(foo)只存在于函数内部,比如,可以用它来做递归运算:
> var fac = function me(x) { return x <= 1 ? 1 : x * me(x-1) }
> fac(10)
3628800
> console.log(me)
ReferenceError: me is not defined
一个命名的函数表达式从表面上看起来,和一个函数声明并没有什么区别.但他们的效果是不同的:一个函数表达式产生一个值(一个函数).一个函数声明执行一个动作:将一个函数赋值给一个变量. 此外,只有函数表达式可以被立即调用,函数声明不可以.
3.3 解决冲突
从3.1和3.2可以看出,有些表达式和语句在表面上看不出有什么区别.也就意味着,相同的代码,出现在表达式上下文和出现在语句上下文会表现出不同的作用.通常情况下,这两种上下文是没有交集的.但是,如果是表达式语句的话,会有一个重叠:也就是说,会有一些表达式出现在语句上下文上.为了解决这种歧义,JavaScript语法禁止表达式语句以大括号或关键字"function"开头:
ExpressionStatement :
[lookahead ∉ {"{", "function"}] Expression ;
那么,如果你想写一个以那些标志开头的表达式语句,该怎办呢? 你可以把它放在一个括号内部,这样并不会改变运行结果,只会确保该表达式被解析在表达式上下文中.让我们看两个例子.第一个例子:eval会按照语句上下文解析它的参数.如果你想让eval返回一个对象,你必须在对象字面量两边加上一个括号.
> eval("{ foo: 123 }")
123
> eval("({ foo: 123 })")
{ foo: 123 }
第二个例子:下面的例子是一个立即执行的函数表达式.
> (function () { return "abc" }())
'abc'
如果你省略了小括号,你会得到一个语法错误(函数声明不可以是匿名的):
> function () { return "abc" }()
SyntaxError: function statement requires a name
如果你添加上函数名,还会得到一个语法错误(函数声明不能被理解执行):
> function foo() { return "abc" }()
SyntaxError: syntax error
另外一个能让表达式在表达式上下文上被解析的办法是使用一元运算符,比如 + 或者 !.但是,和使用括号不同的是,这些操作符会改变表达式的运行结果.如果你不关心结果的话,完全可以使用:
> +function () { console.log("hello") }()
hello
NaN
NaN是+作用在函数执行后的返回值undefined上的结果.
译者注:我觉的没翻译明白,所以用拙劣的水平画了张图.
JavaScript中:表达式和语句的区别的更多相关文章
- JavaScript 中表达式和语句的区别
1.语句和表达式 JavaScript中的表达式和语句是有区别的.一个表达式会产生一个值,它可以放在任何需要一个值的地方,比如,作为一个函数调用的参数.下面的每行代码都是一个表达式: myvar3 + ...
- Javascript中表达式和语句的区别
一.表达式:一个表达式会产生一个值,它可以放在任何需要一个值的地方,比如,作为一个函数调用的参数. 以下例子就是表达式: a=35: b=1+a; a=function (){return 6}: b ...
- Python中表达式和语句及for、while循环练习
Python中表达式和语句及for.while循环练习 1)表达式 常用的表达式操作符: x + y, x - y x * y, x / y, x // y, x % y 逻辑运算: x or y, ...
- JavaScript 中 Property 和 Attribute 的区别详解
property 和 attribute非常容易混淆,两个单词的中文翻译也都非常相近(property:属性,attribute:特性),但实际上,二者是不同的东西,属于不同的范畴. property ...
- 你可能不知道的java、python、JavaScript以及jquary循环语句的区别
一.概述 java循环语句分为四种形式,分别是 while, do/while, for, foreach: python中循环语句有两种,while,for: JavaScript中循环语句有四种, ...
- Javascript中的Label语句
在javascript中,我们可能很少会去用到 Label 语句,但是熟练的应用 Label 语句,尤其是在嵌套循环中熟练应用 break, continue 与 Label 可以精确的返回到你想要的 ...
- Javascript中setTimeout和setInterval的区别和使用
在javascript中,window对象有两个主要的定时方法,分别是setTimeout 和 setInterval,其语法基本上相同,但是完成的功能取有区别. setTimeout方法是定时程序, ...
- 理解javascript中的for语句
程序实现中经常要用到循环语句,其中for循环是多数语言都有的.在javascript中,for循环有几种不同的使用情况,下面就分别来讲述我的理解. 第一种:(通常情况,循环执行相关操作) var ob ...
- [译]Javascript中的switch语句
本文翻译youtube上的up主kudvenkat的javascript tutorial播放单 源地址在此: https://www.youtube.com/watch?v=PMsVM7rjupU& ...
随机推荐
- JS学习 用 arguments 对象模拟函数重载
用 arguments 对象判断传递给函数的参数个数,即可模拟函数重载: function doAdd() { if(arguments.length == 1) { alert(arguments[ ...
- Dota2一直 正在登录服务器的解决办法
然后:1: c:\Windows\System32\drivers\etc\ 2:双击hosts文件,用记事本方式打开3:复制以下并粘贴至以记事本方式打开的hosts最后面111.221.33.253 ...
- you selected does not support x86-64 instruction set
centos 安装redis时报you selected does not support x86-64 instruction set 解决方法 make CFLAGS="-march=x ...
- 「日常训练」Known Notation(ZOJ-3829)
题意与分析 题意是这样的:给一个字符串,字符串中只包含数字和运算符'*'.现在问字符串是不是一个合法的逆波兰式(后缀表达式).已知逆波兰式的空格消除,也就是说123可以看成123也可以看成1和23.如 ...
- MySQL数据库优化方法
一.表类型MyISAM 和 InnoDB的区别 作者:Oscarwin链接:https://www.zhihu.com/question/20596402/answer/211492971来源:知乎著 ...
- XSS----payload,绕过,xss小游戏记录
一.XSS 1.原理:攻击者把恶意的脚本代码注入到网页中,等待其他用户浏览 这些网页(或触发其他条件),从而执行其中的恶意代码. 1.xss实例代码: test.html <!DOCTYPE h ...
- selenium自动化测试资源整理
1. 所有版本chrome下载 是不是很难找到老版本的chrome?博主收集了几个下载chrome老版本的网站,其中哪个下载的是原版的就不得而知了. http://www.slimjet.com/ch ...
- leetcode-回文链表
请判断一个链表是否为回文链表. 示例 1: 输入: 1->2 输出: false 示例 2: 输入: 1->2->2->1 输出: true 进阶:你能否用 O(n) 时间复杂 ...
- python邮件服务-yagmail
下载安装 yagmail import yagmail #链接邮箱服务器 #此处的password是授权码 yag= yagmail.SMTP( user="843092012@qq.c ...
- Java开发中用的比较多的数据结构
java 中几种常用数据结构 2016年07月11日 09:11:27 阅读数:83211 标签: 数据结构java 更多 个人分类: 自行学习 JAVA中常用的数据结构(java.util. 中 ...
