![计算机程序的构造和解释(JavaScript版)](https://wfqqreader-1252317822.image.myqcloud.com/cover/951/50417951/b_50417951.jpg)
1.1.1 表达式
开始学习程序设计时,最简单方法就是观察一些与JavaScript语言解释器交互的典型实例。你键入一个语句,解释器的响应就是把它求值这个语句的结果显示出来。
你可以键入的一种基本语句就是表达式语句,形式上是一个表达式后面跟一个分号。一类最基本的表达式是数(更准确地说,你键入的表达式是一串数字,按照以10为基数的方式表示相应的数值)。如果你输入下面的程序:
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/25_01.jpg?sign=1739305409-NK8OdeFPBZBKhTNJluN5k9mVWgkSRtax-0-f5ad4d5b6dbd4c0b4b34bd325ddf032e)
解释器的响应是打印出[2]
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/25_02.jpg?sign=1739305409-7Jk0Sc3doWX6e5OmDDrP93NPItfSuebe-0-1908cd7d3b10491d57fca993d9babde2)
表示数的表达式可以用运算符(例如+或者*)组合起来,形成复合表达式,表示把相应的基本函数作用于这些数。例如:
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/25_03.jpg?sign=1739305409-nhXNyR7Bb6vySD0gk8TBlAQwAp4hdNUi-0-96b185bfb96e726925530e8b27ef3917)
上面这样的表达式称为组合式,它们以另一些表达式作为其组成部分。这种组合式的形式是把一个运算符符号放在中间,两个运算对象表达式分置左右,这种表达式称为运算符组合式。得到运算符组合式的值的方法,就是把运算符代表的那个函数应用于给定的实际参数(下面常简称为实参),而所谓实际参数就是相应运算对象的值。
把运算符放在两个运算对象之间的约定形式称为中缀记法,这也是常用的数学表示法,这些多半是你早已在小学和日常生活中熟悉了的东西。与在数学中一样,运算符组合式可以嵌套,其中的运算对象本身也可以是运算符组合式:
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_01.jpg?sign=1739305409-oou3Eu6mthobWR5ltZ6S8zycC3ercz5N-0-2e2e6b603e6962ff5e4fba993f1ec79b)
如常,我们可以用括号在运算符组合式里做分组,以避免歧义。如果忽略括号,JavaScript也遵循常规的规则:乘法和除法运算符的组合力比加减法运算符更强,因此,
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_02.jpg?sign=1739305409-S4vJ6ewReKrczWpCPNe3Vrj2yDRMutHm-0-6ba4ba1f506b0109a1dab631fce99c20)
表示
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_03.jpg?sign=1739305409-g2TkgAl4tmINywuZGXJPd5dlrzivpHgf-0-59c5c21070b77b72efd3995a61d2e8b1)
对这种情况,我们说*和/具有比+和-更高的优先级。加或减的序列从左到右地处理,乘和除的序列也一样。这样,
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_04.jpg?sign=1739305409-NS9QIPGwkpi7yFLgYnAZ7gO15iyxshzq-0-50f9c3cb736b9a95838f03ac1ef7c754)
就表示
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_05.jpg?sign=1739305409-6kzg3J6DlJb1X5ZyE2QpslVmCarstRhu-0-df540166dfbaaafda7a24c09edc1bc6b)
对这些情况,我们说运算符+、-、*和/都是左结合的。
原则上说,对于可以求值的表达式嵌套的深度及其整体的复杂程度,JavaScript解释器并没有任何限制。反倒是我们自己可能被一些并不很复杂的表达式搞糊涂,例如:
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_06.jpg?sign=1739305409-QLmPV15ffquyepZy79KgsNu3it6VnhbY-0-e758bd4725c68af6cd72de5b52201cee)
对这样复杂的表达式,解释器马上就能求值得到57。我们帮助自己的方法可能是重写上面的表达式,例如写成下面的形式:
![](https://epubservercos.yuewen.com/1E97F9/29686461304596906/epubprivate/OEBPS/Images/26_07.jpg?sign=1739305409-ZH2jAsIvtuzjgvVcImlZTIiCwZOAWSVw-0-770935adb07e8a54ad2cb9940e80b5a0)
这样就在视觉上区分出了表达式的主要成分。
即使对非常复杂的表达式,解释器也总是按同样的基本循环运作:从终端读入用户键入的一个语句,对该语句求值,然后打印得到的结果。这种运作模式常被说成解释器在运行一个读入-求值-打印循环。可以看到,完全不需要明确要求解释器打印语句的值[3]。