JavaScript 运算符
一、比较运算符
">"、"<"、"=="、">="、"<="、"!="
比较结果为boolean值
计算机的一切运算符,但凡它叫运算符不管是逻辑运算符、计算运算符…,它强调的是运算,其它的都是作为运算的修饰词,
“比较运算符”比较是运算的修饰词叫定语,运算是重要的但凡运算就要求结果的
比如 1 > 2 1大于2是要求结果的,拿个变量就能接收它的结果,结果是什么呢?结果就两个布尔值 true/false 代表比较运算符的结果
var a = 1 > 2; document.write(a); // false
1 < 2 返回结果是true
var a = 1 < 2; document.write(a); // true
只有数字和数字能比吗?
一切东西都能比,只是比较规则需要探究而已
看下面的例子,始皇帝比我大吗?
var a = "秦始皇" > "我本人"; document.write(a); // true
"秦始皇" > "我本人" 比较的是字符串,字符串比较的有它一系列的规则,字符串比的是 ASCII 码(0 - 127)
什么是ASCII码?
ASCII 码最开始有128个,ASCII 码由二进制数来表示,一开始由7位二进制数 0000000 这7个二进制的数能表示 128 个十进制的数
比如 0000001 代表十进制的1,0000010 代表十进制的2,
这七位二进制的数能表示十进制的“0到127”,这0到127每个数都对应的什么东西呢?
0 到 127每个数后面都对应的是一个字符,计算机要比较两个字符,
比如 "a" < "b" 比较的是字符串"a"后面对应的 ASCII 码和"b"后面对应的 ASCII 码它俩谁大。
看一下ASCII码表,a代表97、b代表98…大写A代表65
简单的说字符串比较的就是 ASCII 码的顺序
var a = 'a'; // ASCII:97 var b = 'b'; // ASCII:98 document.write(a > b); // false
补充一下
ASCII 码分 ASCII一码 跟 ASCII 二码,ASCII 二码是 8 位二进制数 128-255(0 - 255),在拓展就拓展到 Unicode 编码
字符串"1"大于字符串"8"吗?
字符串"1"的ASCll码是49,"8"的ASCll码是56
var a = "1" > "8"; document.write(a); // false
字符串"10"和字符串"8"比呢?
字符串"10"不读十,它读字符串"一零"。
奥运会国家出场顺序是按照 26 个字母顺序排的,有很多个 a 开头的国家怎么办呢?比第二个字母。
所以字符串 "10" 符号的原则是先拿开头的 "1" 比较,字符串 "1" 已经小于字符串 "8" 了,就不看第二个字符了,这是字符串比较的原则
var a = "10" > "8"; document.write(a); // false
== 等不等于,是否等于
1是否等于2?把1是否等于2的结果赋到a里面去,但凡比较运算符得的结果是布尔值
var a = 1 == 2; document.write(a); // false
>=、<= 不说了
!= 是否不等于,叹号是非不等于到意思
var a = 1 != 2; document.write(a); // true
下面说一个特殊的原则
数字1等于数字1
var a = 1 == 1; document.write(a); // true
undefined 等于 undefined 返回 true,两边看着视觉上都一样
var a = undefined == undefined; document.write(a); // true
然后看一个
infinity 等于 infinity吗?等于返回 true,计算机里面 infinity 加 1 大于正无穷,是固定值下面
var a = infinity == infinity; document.write(a); // true
再看非数NaN,就NaN这个是特例,NaN不等于任何东西包括自己,这就是定式是一个规则
var a = NaN == NaN; document.write(a); // false
下面的逻辑运算符是本次课程的重点!
二、逻辑运算符
"&&"、"||"、"!"
运算结果为真实的值
这三个"&&"、"||"、"!"是重点叫逻辑运算符
1、与运算符(&&)
&&
与运算符一般是放在 if 判断里面,其实那种用法是变相用法,本质上可以是这样的 var a = "1 && 2" ,一定记住运算符就是要求结果
1 && 2 一般来说两边是真才是真,1和2都是真应该返回true,而结果返回数字2
var a = 1 && 2; document.write(a); // 2
与运算符(&&)有个规则是为了求结果的,它是一定会返回结果,结果怎么返回呢?
这里只研究前后两个表达式的情况,
它会先看“与运算符”前面第一个表达式是一个单独的数也好(1 && 2),是一个计算的表达式(1+1 && 2)也好都算是一个表达式,第一个表达式转换成布尔值的结果如果为真
那么它会看第二个表达转换为布尔值的结果,
然后如果只有两个表达式的话,只看到第二个表达式就可以返回该表达式的值了,如果前面第一个表达式转换成布尔值为真,第二个表达不用看了,直接把第二个表达式的结果返回,也就是说运算结果是2
注意:这六个值 undefined、null、NaN、 ""、0、false,转换成布尔值都是 false
如果前面的运算结果为真,它就会把第二个表达式的运算结果返回,下面第二个表达式是 2 + 2 ?
判断第一个表达式 1 转换成布尔值是真,看第二个表达式的运算结果直接返回,所以a的运算结果是4不会返回true或false,只会返回原本的值这是第一种情况
var a = 1 && 2 + 2; document.write(a); // 4
第二种情况,当第一个表达式0转换成布尔值为false的时候,不再往后走了直接把第一个表达式的值 0 返回
var a = 0 && 2 + 2; document.write(a); // 0
两个表达式的时候就看第一个表达式,如果第一个是真把第二个结果返回,如果第一个是假就把第一个表达式的结果返回
关注一下整体的,下面这个表达式运算完结果的布尔值,如果第一个表达式为假它返回的结果是0,0再转换成布尔值是假
var a = 0 && 1; document.write(a); // 0
如果第一个是真第二个是假,它会返回第二个,不会看第二个是不是假,直接返回第二个0,返回这个0转换成布尔值还是假
var a = 1 && 0; document.write(a); // 0
所以那句顺口溜是这么来的,是关注它的结果“全真才为真,有一个假就是假”是片面抽象完后的结果,如果关注值返回的是真实得值,只不过把值转换成布尔值,才出现这句话全真才为真,有一个假就是假。
var a = 1 && 1; document.write(a); // 1 var a = 1 && 0; document.write(a); // 0 var a = 0 && 1; document.write(a); // 0
如果是三个表达式或多个表达式呢?它会按照这个规则依次往后看
先看第一个表达式是否为真,如果为真看第二个表达式,如果第二个的表达式也为真,它会看第三个表达式,也就是说它往后走的原则是,当是真的就往后走,一旦遇到假的就返回假的值。
下面第一个是真看第二个,第二个表达式也是真看第三个,第三个表达式如果是最后一个直接把结果返回
var a = 1 && 1 && 1; document.write(a); // 1
如果当第一个为假呢?那就直接返回第一个表达式的值
var a = 0 && 1 && 1; document.write(a); // 0
如果第一个不是假,第二个是假false呢?那到第二个表达式就中断了,遇到假的就停并返回值
var a = 1 && false && 1; document.write(a); // false
所以连成串也是符合那个道理,有一个假就是假,全真才为真,这就是“与运算符”
“与运算符”还可以复杂点
什么是运算符?运算符就是两侧还可以兼容其它运算符
var a = 1 + 1 && 1 - 1; document.write(a); // 0
与运算符(&&)的高级的用法
与运算符有中断的作用,如果前面是0就不看后面的了,这是一种中断,与运算符两侧只写上表达式就可以,这个表达式可以是数字运算、计算、也可以是一种函数的写法或打印出东西的写法都行。
下面用“与运算符”不在接收它的返回值了,只拿它当做一种短路语句来用,什么是短路语句?如果…那么…
换句话说我只关注它能不能读到第二句,如果它能读到第二句就执行,读不到就不执行
0 && document.write('打印');
这样方便做一个判断,如果2大于1就打印出后面的语句,这样不关注返回值只关注执行顺序
2 > 1 && document.write('二大于一符合条件打印了');
不关注返回值,这时候它就变成了“短路语句”,如果前面是假的后面就不执行,如果前面是真才执行后面的内容跟短路了一样,虽然跟if语句差不多,这里我们叫它短路语句,它是if的简写形式,if的表达形式太过复杂。
一般公司里处理需求的时候,后端会给前端传数据,前端拿到后端给的数据以后放到页面里面去,但后端的传的数据有时候是不靠谱的,有时候数据是空的或错误数据,所以前端拿到数据的时候先判断一下,数据是有还是没有,没有就不能处理否则会报错,这时候就要短路语句来处理。
var data = ...; // 执行一个语句会用到data // 但是不能直接执行,要先判断data有没有意义才执行 data && 执行一个语句 // 如果data是空的,变量是没有值是undefinde转化布尔值false,就不会不执行到下面去 // 执行这个语句得到一个保障,只要前面的值有意义才执行没意义的不执行,这是短路语句的一个基本应用
一般在公司里是这样写的,ajax传的参数
data && fn(data); // 参数传过来才有意义,如果参数没有意义程序就瘫痪了,所以判断一下传过来在执行。
单独的与"&"真实的开发中没有用,知道有这样一个存在!
//有一种高大上的运算叫与运算,二进制什么的没懂!!! var a = 1 & 2; document.write(a);//0
2、或运算符“||”
或运算符和与运算符大致差不多,但有点东西是相反的,或运算符先看第一个表达式是不是真,如果是真就不往后看了并把值返回(1),或运算符它是碰到真就返回
var num = 1 || 3; document.write(num); // 1
第一个表达式是4,或运算符它根本不看第二个表达式,遇到真就返回4
var num = 4 || 3; document.write(num);// 4
第一个表达式是0呢?碰到假就往后看寻找一个真返回,如果有两个表达式第一个为假,第二个不管是什么都得返回第二个,所以第二个用不着看了直接返回3
var num = 0 || 3; document.write(num); // 3
如果第一个表达式是数字0第二个是false呢?一共就两个表达式,只能返回最后一个false了
var num = 0 || false; document.write(num); // false
这里也符合原则,如果关注这个“与逻辑运算符”它运算完结果的值,结果的布尔值有一个真就为真,全假才为假
var num = 0 || false || 1; document.write(num);// 1
|| 有一个真就是真,全假才为假,“或运算符”碰到真就停。
&& 全真才为真,有一个假就为假,“与运算符”碰到假就停。
var num = 0 || false || 2 || 1; document.write(num); // 2
工作中“或运算符”写兼容
div.onclick = function(ev){ // var event = ev; 在标准浏览器,事件对象ev直接写就可以了 // var event = ev; 在IE浏览器ev不好使,事件对象存在window.event var event = ev || window.event; // 写一个兼容,在所有浏览器里事件对象都好使,如果遇到ev里面有值就不往后看了,没有值就往后看window.event }
3、非运算符 "!"
“非”就是否的意思,非的意思就是先把这个东西转换成布尔值在取反,不管是什么数据类型,先转换成布尔值在取反。
123转布尔值为true,true在取反为false
var a = !123; document.write(a); // false;
空字符串是false,取反后为true
var a = !""; document.write(a); // true
下面难一点的“!!”
“非非”意思是变布尔值取反,在把布尔值再取反
var a = !!""; document.write(a); // false;
验证一下“非非”取反再取返,把结果是false的6个值都验证一下
var a = !!0; document.write(a); // false; var a = !!NaN; document.write(a); // false; var a = !!null; document.write(a); // false; var a = !!undefined; document.write(a); // false; var a = !!false; // false不用说也是false document.write(a); // false;
下面a最后得的是什么?a是false,自身取反赋给自身
var a = true; a = !a; document.write(a); // false;
有没有“非等于”?没有,下面这是表达a、b它俩个等不等
a != b;