学习操作符这个章节最好回忆一下C里的惯例,因为ECMAScript的标准很多继承自C的语法

一元操作符

只能操作一个值得操作符

递增和递减操作符

var age = 29;

++age; //30

var age = 29;

age = age +1; //30

var age = 29;

--age;  //28

var age = 29 ;

var anotherAge = –-age +2;

alert (age);   //28

alert(anotherAge); //30

var age = 29;

age++;  // 先求值再增加1

var num1 = 2;

var num2 = 20;

var num3 = num1--  + num2;   //等于22

var num4 = num1 + num2;    //等于21

以上四个操作符对任何值都适用,也就是他们不仅适用于整数,还可以用于字符串, 布尔值, 浮点数值和对象。 在应用于不同的值时,递增和递减操作符遵循下列规则、

  • 在应用与一个包含有效数字字符的字符串时,先将其转换为数字值,再进行加减1的操作。 字符串变量变成数值变量。
  • 在应用与一个不包含有效数字字符的字符串时,将变量的值设置为NaN,字符串变量变成数值变量
  • 在应用于布尔值false时, 先将其转换为0再执行加减1的操作。 布尔值变量变成数值变量。
  • 在应用于布尔值true时,先将其转换为1再执行加减1的操作。 布尔值变量变成数值变量。
  • 在应用于浮点数值时, 执行加减1的操作。
  • 在应用于对象时,先调用对象的valueOf()方法,以取得一个可供操作的值。 然后对该值应用前述规则。如果结果是NaN, 则调用toString()方法后再应用前述规则, 对象变量变成数值变量。

以下示例展示了上面的规则:

var s1 = “2”;

var s2 = “z”;

var b = false;

var f = 1.1;

var o = {

valueOf: function() {return –1;}

};

s1++;  //3

s2++;  //NaN

b++;   //1

f- - ;   //值变成0.10000000000000009(由于浮点舍入错误所致)

o- -;   // –2

一元加和减操作符

在对非数值应用一元加操作符时,该操作符会像Number()转型函数一样对这个值执行转换。 换句话说,布尔值false和true将被转换为0和1, 字符串值会被按照一组特殊的规则进行解析, 而对象是先调用他们的valueOf()和toString()方法,在转换得到的值。

下面是一些例子:

var s1 = “01”;

var s2 = “1.1”;

var s3 = “z”;

var b = false;

var f = 1.1;

var o = {

valueOf: function() {

return –1;
}

};

s1 = +s1;       //值变成数值1

s2 = +s2;       //值变成数值1.1

s3 = +s3;       //值变成NaN

b = +b;          //值变成数值0

f = +f ;           //值未变,仍然是1.1

o = +o;           //值变成数值-1

一元减操作符和一元加操作符的用法类同,不再啰嗦。

布尔操作符

一共有三个: 非(NOT), 与(AND), 和或(OR)。

逻辑非

逻辑非用一个感叹号(!)表示, 可用于ECMAScript中的任何值, 无论这个值是什么数据类型, 这个操作符都会返回一个布尔值。 首先将它的操作数转换为一个布尔值, 然后再对其求反。也就是说,逻辑非遵循下列规则:

  • 如果操作数是一个对象, 返回false;
  • 如果操作数是一个空字符串,返回true;
  • 如果操作数是一个非空字符串, 返回false;
  • 如果操作数是数值0 , 返回true;
  • 如果操作数是任意非0数值(包括infinity), 返回false;
  • 如果操作数是null, 返回true;
  • 如果操作数是NaN, 返回true;
  • 如果操作数是undefined, 返回true。

下面的示例展示上述规则的结果

alert(!false);  //true

alert(!”blue”);  //false

alert(!0);   //true

alert(!NaN);  //true

alert(!””);  //true

alert(!12345);  //false

逻辑与

&&操作可以应用于任何类型的操作数而不仅仅是布尔值。 在有一个操作数不是布尔值的情况下,逻辑与操作就不一定返回布尔值, 此时,他遵循下列规则;

  • 如果第一个操作数是对象, 则返回第二个操作数;
  • 如果第二个操作数是对象, 则只有在第一个操作数的求值结果为true的情况下才会返回该对象;
  • 如果两个操作数都是对象, 则返回第二个操作数;
  • 如果有一个操作数是null, 则返回null;
  • 如果有一个操作数是NaN, 则返回NaN;
  • 如果有一个操作数是undefined, 则返回undefined。

逻辑与属于短路操作,如果第一个操作数为false, 无论第二个操作数是什么值,结果都不再可能是true了。

再看下面的例子;

var found = true;

var result = (found && someUndefinedVariable);  //这里会发生错误,

alert(result);   //这一行不会执行,

因为变量someUndefinedVariable没有声明。 由于变量found的值是true, 所以逻辑与操作符会继续对变量someUndefinedVariable求值。 但是someUndefinedVariable尚未定义,因此会导致错误。

逻辑或

逻辑或操作符由两个竖线符号(||)表示, 有两个操作数。

和逻辑操作相似,如果有一个操作数不是布尔值, 逻辑或也不一定返回布尔值; 此时,他遵循下列规则:

  • 如果第一个操作数是对象, 则返回第一个操作数;
  • 如果第一个操作数的求值结果是false, 则返回第二个操作数;
  • 如果两个操作数都是对象,则返回第一个操作数;
  • 如果两个操作数都是null, 则返回null;
  • 如果两个操作数都是NaN,则返回NaN;
  • 如果两个操作数都是undefined, 则返回undefined。

与逻辑与操作符相似,逻辑或操作符也是短路操作符。也就是说, 如果第一个操作数的求值结果为true, 就不会对第二个操作数求值。

可以利用逻辑或的这个 行为来避免为变量赋null或undefined值。 例如;

var myObject = preferredObject || backupObject;

在这个例子中,变量myObject将被赋予等号后面两个值中的一个。 变量preferredObject中包含优先赋给变量myObject的值, 变量backupObject负责在preferredObject中不包含有效值的情况下提供后备值。如果preferredObject的值不是null, 那么它的值将被赋给myObject, 如果是null, 则将backupObject的值赋给myObject。 ECMAScript程序的赋值语句经常会用这种模式。

乘法操作符

在处理特殊值的情况下,乘法操作符遵循下列特殊的规则:

  • 如果操作数都是数值, 执行常规的乘法运算, 即两个正数或两个负数相乘的结果还是正数, 而如果只有一个操作数有负号,那么结果就是负数。 如果乘积超过了ECMAScript数值的表示范围,则返回Infinity, 或-Infinity;
  • 如果有一个操作数是NaN, 则结果是NaN;
  • 如果是Infinity与0相乘, 则结果是NaN;
  • 如果是Infinity与非0数值相乘, 则结果是Infinity或-Infinity, 取决于有符号数操作数的符号;
  • 如果是Infinity与Infinity相乘,则结果是Infinity;
  • 如果有一个操作数不是数值, 则在后台调用Number()将其转换为数值,然后再应用上面的规则。

除法操作符

和乘法操作符类似,除法操作符对特殊的值也有特殊的处理规则, 这些规则如下:

  • 如果有一个操作数是NaN, 则结果是NaN;
  • 如果是Infinity被Infinity除,则结果是NaN;
  • 如果是Infinity被任意数值除,则结果是Infinity;
  • 如果是零被零除,则结果是NaN;
  • 如果是非零的有限数被零除, 则结果是Infinity或-Infinity, 取决于有符号操作数的符号。
  • 如果是Infinity被任何非零数值除, 则结果是Infinity或-Infinity,取决于有符号操作数的符号;
  • 如果有一个操作数不是数值,则在后台调用Number()将其转换为数值, 然后再应用上面的规则。

求模

求模(余数)操作符由一个百分号(%)来表示,遵循下面的规则;

  • 如果操作数都是数值,执行常规的除法运算, 返回除得的余数;
  • 如果被除数是无穷大值而除数是有限大的数值,则结果是NaN;
  • 如果被除数是有限大的值,而除数是零,则结果是NaN;
  • 如果是Infinity被Infinity除,则结果是NaN;
  • 如果被除数是有限大的数值而除数是无穷大的数值,则结果是被除数;
  • 如果被除数是0,则结果是0;
  • 如果有一个操作数不是数值,则在后台调用Number()将其转换为数值, 然后再应用上面的规则。

加法操作符

如果两个操作符都是数值, 执行常规的加法计算, 然后根据下列规则返回结果:

  • 如果有一个操作数是NaN, 则结果是NaN;
  • 如果是 Infinity 加 Infinity, 则结果是 Infinity;
  • 如果是 –Infinity 加 -Infinity, 则结果是 -Infinity;
  • 如果是Infinity 加 –Infinity, 则记过是NaN;
  • 如果是 +0 加 +0,则结果是+0;
  • 如果是 –0 加 -0, 则结果是 -0;
  • 如果是 +0 加 -0, 则结果是 +0.

如果有一个操作数是字符串, 那么就要应用如下规则:

  • 如果两个操作数都是字符串,则将第二个操作数与第一个操作数拼接起来;
  • 如果只有一个操作数是字符串,则将另一个操作数转换为字符串,然后再将两个字符串拼接起来。

如果有一个操作数是对象,数值,或布尔值, 则调用他们的toString()方法取得相应的字符串值, 然后再应用前面关于字符串的规则,对于undefined和null,则分别调用String()函数并取得字符串“undefined”和“null”。

值得注意的示例:

var num1 = 5;

var num2 = 10;

var message = “The sum of 5 and 10 is  “ + num1 + num2 ;

alert(message) ;    // “The sum of 5 and 10 is 510”   字符串操作的结果,若想对数值执行算术计算, 然后再将结果和字符串拼接起来,应该像下面这样使用圆括号:

var  num1 = 5;

var  num2 = 10;

var  message = “The sum of 5 and 10 is “+(num1 + num2);

alert(message); // ”The sum of 5 and 10  is 15”

减法操作符

与加法操作符类似, ECMAScript中的减法操作符在处理各种数据类型的转换时,同样需要遵守一些特殊的规则, 如下所示:

  • 如果两个操作数都是数值,则执行常规的算术减法操作并返回结果;
  • 如果有一个操作数是NaN, 则结果是NaN;
  • 如果是Infinity 减 Infinity,则结果是NaN;
  • 如果是 –Infinity 减 -Infinity, 则结果是NaN;
  • 如果是 Infinity 减 -Infinity, 则结果是 Infinity;
  • 如果是 –Infinity 减 Infinity, 则结果是 -Infinity;
  • 如果是+0 减+0, 则结果是+0;
  • 如果是+0 减 -0, 则结果是-0;
  • 如果是-0 减 -0, 则结果是 +0;
  • 如果有一个操作数是字符串,布尔值,null, 或undefined,则先在后台调用Number()函数将其转换为数值, 然后再根据前面的规则执行减法计算, 如果转换的结果是NaN,则减法的结果就是NaN;
  • 如果一个操作数是对象,则调用对象的valueOf()方法以取得表示该对象的数值。 如果得到的值是NaN, 则减法的结果就是NaN。如果对象没有valueOf()方法,则调用其toString()方法并将得到的字符串转换为数值。

下面的例子展示了上面的规则

var result1 = 5 – true ;   //4, 因为true被转换成1

var result2 = NaN –1;     //NaN

var result3 = 5 –3;        //2

var result4 = 5 – “”;      //5, 因为“”被转换成了0

var result5 = 5 – “2”;    //3, 因为“2” 被转换成了2

var result6 = 5 – null;   //5, 因为null被转换成了0

关系操作符

与ECMAScript中的其他操作符一样,当关系操作符的操作数使用了非数值时,也要进行数据转换或完成某些奇怪的操作,以下就是相应的规则:

  • 如果两个操作数都是数值,则执行数值比较;
  • 如果两个操作数都是字符串, 则比较两个字符串对应的字符编码值;
  • 如果一个操作数是数值, 则将另一个操作数转换为一个数值,然后执行数值比较;
  • 如果一个操作数是对象, 则调用这个对象的valueOf()方法,用得到的结果按照前面的规则执行比较。 如果对象么有valueOf()方法,则调用toString()方法, 并用得到的结果根据前面的规则执行比较;
  • 如果一个操作数是布尔值, 则先将其转换为数值,然后再执行比较。

请仔细体会以下示例:

var result = “Brick” <”alphabet”;   //true  因为大写字符的编码都比小写字符编码小

var result =  “Brick”.toLowerCase() < “alphabet”.toLowerCase(); //false  都转换成小写字母后就可得到想要的结果。

var result = “23” <”3”; //true

var result = “23” < 3 ; //false,  “23”会转换成数值23然后再与3进行比较,因此就会得到合理的结果。

var result = result = “a” <3 ; //false, 因为”a”被转换成了NaN

var result = NaN < 3; //false

var result = NaN >= 3; //false   这个没有什么道理可说,和NaN进行比较就返回false。

相等操作符

1)相等和不相等

ECMAScript中的相等操作符由两个等于号(==)表示,如果两个操作数相等,则返回true。 而不相等操作符由叹号后跟等于号(!=)表示, 如果两个操作数不相等, 则返回true。 这两个操作符都会先转换操作数(通常称为强制转换), 然后再比较他们的相等性。

在转换不同的数据类型时,相等和不相等操作遵循下列基本规则:

  • 如果有一个操作数是布尔值, 则在比较相等性之前先将其转换为数值--false转换为0, 而true转换为1;
  • 若果一个操作数是字符串, 另一操作数是数值,在比较相等性之前先将字符串转换成数值;
  • 如果一个操作数是对象,另一个操作数不是,则调用对象的valueOf()方法,用得到的原始值按照前面的规则进行比较;

这个两个操作数在进行比较时要遵循下列规则。

  • null 和 undefined是相等的。
  • 要比较相等性之前,不能将null和undefined转换成其他值。
  • 如果有一个操作数是NaN, 则相等操作符返回false, 而不相等操作符返回true。 即使两个操作数都是NaN, 相等操作符也返回false, 因为按照规则,NaN不等于NaN。
  • 如果两个操作数都是对象,则比较他们是不是同一个对象。如果两个操作数都指向同一个对象, 则相等操作符返回true, 否则, 返回false。

2)全等和不全等

除了在比较之前不转换操作数之外, 全等和不全等操作符与相等和不相等操作符没有什么区别。 全等操作符由3个等于号(===)表示, 它只在两个操作数未经转换就相等的情况下返回true,如下面例子;

var result1 = (“55” == 55);   //true ,因为转换后相等

var result2 = (“55” ===55); //false, 因为不同的数据类型不相等

var result3 = (“55” != 55);   //false, 因为转换后相等

var result4 = (“55”!== 55);  //true, 因为不同的数据类型不相等

由于相等和不相等操作符存在类型转换问题,而为了保持代码中数据类型的完整性。 我们推荐使用全等和不全等操作符。

Javascript操作符的内容到此为止

Javascrpt核心概念(2)--操作符的更多相关文章

  1. 学习 JavaScript (四)核心概念:操作符

    JavaScript 的核心概念主要由语法.变量.数据类型.操作符.语句.函数组成,前面三个上一篇文章已经讲解完了.后面三个内容超级多,这篇文章主要讲解的是操作符. 操作符 什么叫做操作符? 这是一种 ...

  2. [程序设计语言]-[核心概念]-02:名字、作用域和约束(Bindings)

    本系列导航 本系列其他文章目录请戳这里. 1.名字.约束时间(Binding Time) 在本篇博文开始前先介绍两个约定:第一个是“对象”,除非在介绍面向对象语言时,本系列中出现的对象均是指任何可以有 ...

  3. 《JavaScript核心概念》基础部分重点摘录

    注:<JavaScript核心概念>适合深入了解JavaScript,比我买的<JavaScript框架设计>语言和内容丰富多了(可能是我水平尚浅吧). 1. 作用域 var ...

  4. 通过核心概念了解webpack工作机制

    webpack 是一个现代 JavaScript 应用程序的静态模块打包器(module bundler).当 webpack 处理应用程序时,它会递归地构建一个依赖关系图(dependency gr ...

  5. 学习 JavaScript (三)核心概念:语法、变量、数据类型

    JavaScript 的核心概念主要由语法.变量.数据类型.操作符.语句.函数组成,这篇文章主要讲解的是前面三个,后面三个下一篇文章再讲解. 01 语法 熟悉 JavaScript 历史的人应该都知道 ...

  6. TensorFlow.js之安装与核心概念

    TensorFlow.js是通过WebGL加速.基于浏览器的机器学习js框架.通过tensorflow.js,我们可以在浏览器中开发机器学习.运行现有的模型或者重新训练现有的模型. 一.安装     ...

  7. javascript 核心概念(1)-数据类型

    语法 (1)到现在为止,大多数浏览器也还是支持到ECMAScript 第三版的标准. 核心概念就是一个语言的基本工作原理,涉及语法,操作符,数据类型. (2)javascript的一切--变量,函数名 ...

  8. Combine 框架,从0到1 —— 1.核心概念

      本文首发于 Ficow Shen's Blog,原文地址: Combine 框架,从0到1 -- 1.核心概念.     内容概览 前言 核心概念 RxSwift Combine 总结 参考内容 ...

  9. 领域驱动设计(DDD)部分核心概念的个人理解

    领域驱动设计(DDD)是一种基于模型驱动的软件设计方式.它以领域为核心,分析领域中的问题,通过建立一个领域模型来有效的解决领域中的核心的复杂问题.Eric Ivans为领域驱动设计提出了大量的最佳实践 ...

随机推荐

  1. 腾讯云,搭建LNMP环境

    LNMP代表的就是:Linux系统下Nginx+MySQL+PHP这种网站服务器架构. Linux是一类Unix计算机操作系统的统称,是目前最流行的免费操作系统.代表版本有:debian.centos ...

  2. 2.2 为什么要使用Shell脚本

        使用脚本编程语言的好处是,它们多半运行在比编译型语言还高的层级,能够轻易处理文件与目录之类的对象.缺点是:它们的效率通常不如编译型语言.不过权衡之下,通常使用脚本编程还是值得的:花一个小时写成 ...

  3. 学习笔记——TCP“三次握手”和“四次挥手”,简单介绍

    TCP/IP协议中,TCP协议提供可靠的连接服务,采用“三次握手”建立一个连接. (1)第一次握手:客户端发送SYN包(SYN=j)到服务器,并进入SYN_SEND状态,等待服务器确认. (2)第二次 ...

  4. Oracle-统计数据库表数据总数量

    create or replace procedure prc_table_count(p_flag out varchar2) AS TCOUNT number; SCOUNT number; CO ...

  5. iptables防火墙原理详解+mysql pt工具

    http://seanlook.com/2014/02/23/iptables-understand/

  6. 机器学习1k近邻

    自己一直学习计算机视觉方面的东西,现在想学习一下数据挖掘跟搜索引擎,自己基础也有点薄弱,看朱明的那本数据挖掘,只能片面的了解这个数据挖掘.不过最近有一本书 机器学习实战,于是乎通过实战的形式了解一下基 ...

  7. AngularJS:日期转换字符

    JS有很多类库提供日期转换函数,AngularJS也不例外.可以通过$filter来完成转换,方法如下: $filter('date')(sourceDate, "yyyy/MM/dd&qu ...

  8. Codeforces Round #305 (Div. 2) C题 (数论)

    C. Mike and Frog time limit per test 1 second memory limit per test 256 megabytes input standard inp ...

  9. 在imageView依次加入7个手势, 1.点击哪个button,往imageView上加入哪个手势.(保证视图上仅仅有一个手势). 2.轻拍:点击视图切换美女图片.(imageView上首先展示的美女

    // // ControlView.h // HomeworkGestureRecognizer // // Created by lanouhn on 14-8-27. // Copyright ( ...

  10. 一篇文章贯穿ACE各种发送接收组件 1.2版

    TCP通信过程介绍 首先介绍一下socket通信的基本过程:这里先如果有两个家伙在通信,一个是S.还有一个叫C (1)S打开port监听本地的port看看有没有人来连接: (2)与此同一时候C试图去连 ...