JavaScript中的运算符

145 阅读5分钟

算术运算符

和其他语言一样,所以我这里只是列出来

  • + 对数字进行求和,或者是拼接字符串
  • - 对数字取负值,或者进行相减
  • * 乘法运算
  • / 除法运算
  • % 取余运算

一些特殊的运算符

  • ** 表示次方运算

自增自减

  • -- 表示递减操作
  • ++ 表示递增操作
  • 自增自减会根据位置,决定是先运算还是先输出

关系运算符

  • > 大于
  • < 小于
  • >= 大于等于
  • <= 小于等于
  • == 等于
  • === 全等于
  • != 表示不等于
1== true // true
5 == true // false
1 === true // false

位运算符

  • & 按位进行与操作
  • ^ 异或运算符
  • | 或运算符
  • >> 按位进行 向右移动
  • << 按位进行 向左移动
  • >>> 无符号右移
7|11 // 7 按位运算,结果为 15
// 7 转换为二进制是 111 ,11 转换为二进制是 1011
//   111
//  1011
// 每一位进行 或 运算,得到结果为
//  1111 // 转为十进制为 15
3&2 // 2
2^1 // 3
1<<2 // 4

逻辑运算符

基本运算符

  • 与运算符 &&
  • 或运算符 ||
  • 非运算符 !
  • 空值合并运算符 ??
// 与运算符的赋值
const state = true
const content = '这里是一些内容'
const result1 = state && content 
const result2 = content && state
// 与运算符也会返回第一个为 false 的内容,如果没有为 false 的内容,返回最后一个
result1 // '这里是一些内容'
result2 // true
// 或运算符的赋值
const result3 = true || '996'
const result4 = false || '996'

运算符的简写

x &&=y 相当于 x && (x=y)

x ||=y 相当于 x || (x=y)

x ??=y 相当于 x ?? (x=y)

let x = 0
x &&=9   // 0
x ||=12  // 12
x ??=55  // 0

空值合并运算符

?? 两个问号

用于解决 || 运算符无法应对的情况,|| 中,只要转成 Boolean 后是 false,左侧的值就会被忽略

let age = 0 || 20
age // 20
let age = '' || null

空值合并预算符只有左侧为 null 或者 undefined 会取右侧的值

let age = 0 ?? 20
age // 0

三步运算符

let x = 10
x>0?x=999:x='wtf'
x // 999
x = x>0?-x:x
x // -999

可选链操作符

ES2020 引入

obj.name?.

let obj = {
  name:{
    firstName:'zhang'
  }
}
obj.name.firstName // 一般是这样取值,但是如果不存在 name 无法取值并且报错
// 为了防止报错通常采用以下两种方法
// 1. 使用 if 进行判断
if(obj){
  if(obj.name){
    let name1 = obj.name.firstName
  }
}
// 2.利用 && 运算符的特性
let name2 = obj && obj.name && obj.firstName
// 用了该符号,一次性解决
let name3 = obj?.name?.firstName 

数值分隔符

_ 可以将数字分割,进行声明,方便查看,可以用于多种进制

注:两侧必须都要有数值

let num = 3146_46446 
let num1 = 31_n  // error 错误书写格式
let num2 = 0x_664 // error 错误书写格式

展开运算符

Spread syntax,可以进行扩展

Math.max(...[1,2,3]) // 3

对象中的应用

可以应用在解构赋值,但是只能应用在最后一个变量上,被接受的值会直接赋值过去,没被接受的会全部复制到展开运算符后的声明数中

let {fall, ...y} = {dear:'55',fall:'23',b:'2',c:3}
y // {b:'2',c:3}

实现对象的合并

let a = {name:'fall'}
let b = {age:'23'}
let info = {...a,...b} 
info //{ name: "fall", age: "23" }

数组中的应用

数组的解构赋值

let [a, b, c = 'c'] = '12'
console.log(a, b, c)  // '1' '2' 'c'

解构

解构数组的声明

// 结构数组的声明
var [x,y,z] = [10,22,33]
console.log(x+'----'+z )
var [x,y,[a,b],z] =[11,22,[],33]
// 结构函数的声明
var {toFixed:ss} = 1000
// 实际上 此时 ss === Number.prototype.toFixed

解构的便利

// 1. 交换变量的值
var [a,b] = [11,22];
[a,b] = [b,a];
alert(a+' and '+b);
// 2. 可以返回多个变量的值
function etc(){
    return ['acj','txt','fbi'];
}
var [r1,r2,r3] =etc()
// 3.解决必须通过固定格式书写的问题
// 参数可以传入默认值
// 固定格式书写
function file(name,age,gender){
    alert('我叫'+name+',今年'+age+'岁,性别是'+gender);
}
file('小明',55,'男');
// 非固定格式书写
function file({name,age,gender = 'boy'}){
    alert('我叫'+name+',今年'+age+'岁,性别是'+gender);
};
file({
    name:'小明',
    gender:'男',
    age:22,
})
// 注,至少传入一个对象才能成功地调用方法
file({})
// 4.快速取出数组
var arr = [11,22,33,44,55];
var {0:first,4:last} = arr;
alert(first);
alert(last == arr[4]);

获取数据类型上的方法

let {toFixed: tf} = 10
// 获取到 10 上的 toFixed 方法,并将该方法赋给 tf
console.log(tf.call(Math.PI, 2))  // 3.14

布尔值解构

let {toString: ts} = true
console.log(ts.call(false))  // 'false'

数组解构:等号右侧的数据具有 Iterator 接口可以进行数组形式的解构赋值;

// 解构不成功的变量值为 undefined
let [a, b, c] = [1, 2]
console.log(a, b, c)  // 1, 2, undefined// 可以设置默认值
let [x, y, z = 3] = [1, 2, null]
console.log(x, y, z)  // 1, 2, null

什么样的数据具有 Iterator 接口呢?如果一个对象能够通过 [Symbol.iterator] 访问,且能够返回一个符合迭代器协议的对象,那么该对象就是可迭代的。目前内置的可迭代对象有:String、Array、TypeArray、Map、Set、arguments 和 NodeList 等。

  • 对象解构:与数组按照索引位置进行解构不同,对象解构是按照属性名进行解构赋值,如果在当前对象属性匹配不成功则会去对象的原型属性上查找:
// 默认写法
let { name: name, age: age } = { name: '布兰', age: 12 }
// 简写
let { name, age } = { name: '布兰', age: 12 }
// 改名且设置默认值
let { name: name1, age: age1 = 12 } = { name: '布兰' }
console.log(name1, age1)  // '布兰' 12
  • 函数参数解构:其实就是运用上面的对象解构和数组解构规则;

    function move({x = 0, y = 0} = {}) {
        console.log([x, y])
        return [x, y];
    }
    move({x: 3, y: 8})  // [3, 8]
    move({x: 3})        // [3, 0]
    move({})            // [0, 0]
    move()              // [0, 0]
    

解构要点

  • 只要等号两边的模式相同(同是对象或同是数组),则左边的变量会被赋予对应的值;
  • 解构不成功的变量值为 undefined
  • 默认值生效的前提是当等号右边对应的值全等于 undefined 的时候;
  • 只要等号右边的值不是对象或者数组,则会进行自动装箱将其转成对象;
  • nullundefined 都无法转成对象,所以无法解构。

解构应用

  • 交换变量的值;

    let x = 1, y = 2;
    [x, y] = [y, x]
    console.log(x, y)  // 2 1
    
  • 通过函数返回对象属性

    function getParams() {
        return {
            name: '布兰',
            age: 12,
        }
    }
    let {name, age} = getParams()
    
  • 通过定义函数参数来声明变量

    let person = {
        name: '布兰',
        age: 12
    }
    init(person)
    ​
    // 普通用法
    function init(person) {
        let {name, age} = person
    }
    ​
    // 更简洁用法
    function init({name, age}) {}
    
  • 指定函数参数默认值

    function initPerson({name = '布兰', age = 12} = {}) {
        console.log(name, age)
    }
    initPerson()  // '布兰' 12
    initPerson({age: 20})  // '布兰' 20
    
  • 提取 JSON 数据

    let responseData = {
        code: 1000,
        data: {},
        message: 'success'
    }
    ​
    let { code, data = {} } = responseData
    
  • 遍历 Map 结构

    let map = new Map()
    map.set('beijing', '北京')
    map.set('xiamen', '厦门')
    ​
    for (let [key, value] of map) {
        console.log(key, value)
    }
    
  • 输入模块的指定方法和属性

    const { readFile, writeFile } = require("fs")
    

参考文章

文章名称链接
「建议收藏」送你一份精心总结的3万字ES6实用指南(上)juejin.cn/post/689589…

\