Javascript零散知识回顾【持续更新】

204 阅读6分钟

位操作符

ECMAScript所有数字都以IEEE-754 64位格式存储,操作符先将64位转为32位整数,然后执行操作,其中第32位为符号位(正数0负数1)

正数直接转二进制存储,负数求正数二进制补码

Number.toString(2)负数表示直接正数二进制加负号

const a = -3;
console.log(a.toString(2));//-11

NaN和Infinity值应用位操作,被当作0处理

  • 按位非(NOT) 返回数值的反码 【~数值】 本质就是操作数的负值-1
  • 按位与(AND) 【数值&数值】

  • 按位或(OR) 【数值|数值】

  • 按位异或(XOR)【数值^数值】

  • 左移 【数值<<位数】 将二进制左移一定位数,左移不会影响符号位,只是正数左移并增加负号
// 2 -> 10 -> 10 0000 -> 32
console.log(2<<4);//32
console.log(-2<<4);//-32
  • 有符号右移 【数值>>位数】右移空出的位置以符号位填充(正数填充0负数填充1) 恰好与左移相反
console.log(32>>4);//2
console.log(-32>>4);//-2
  • 无符号右移 【数值>>>位数】右移空出位置以0填充

基本类型转换和运算规则

boolean

Number

后面的数值操作符都基于此处规则

String
  • 有toString方法直接调用
  • null和undefined返回"null"和"undefined"
乘号
  • number * number 常规,超出范围±Infinity
  • 其中一个NaN,返回NaN
  • Infinity * 0,返回NaN
  • Infinity * 非0,返回Infinity
  • Infinity * Infinity,返回Infinity
  • 有一个不是数值则调用Number()规则转为数值再应用上面规则
除号
  • number * number 常规,超出范围±Infinity
  • 其中一个NaN,返回NaN
  • Infinity / Infinity,返回NaN
  • 0 / 0,返回NaN
  • 0 / 非零有限数,返回Infinity或-Infinity
  • 非零有限数 / Infinity,返回Infinity
  • 有一个不是数值则调用Number()规则转为数值再应用上面规则
求余
  • number % number 常规
  • Infinity % number,返回NaN
  • number % 0,返回NaN
  • Infinity % Infinity,返回NaN
  • number % Infinity,返回number
  • 0 % anyNumber,返回0
  • 有一个不是数值则调用Number()规则转为数值再应用上面规则
求和
  • NaN + any,返回NaN
  • Infinity + Infinity,返回Infinity
  • -Infinity + -Infinity,返回-Infinity
  • Infinity + -Infinity,返回NaN
  • +0 + +0,返回+0
  • -0 + -0,返回-0
  • +0 + -0,返回+0
  • string + string,字符拼接
  • string + any, String(any) 字符拼接 详情见其他转字符串
减法
  • number - number 常规
  • 有一个NaN,返回NaN
  • Infinity - Infinity,返回NaN
  • -Infinity - -Infinity,返回NaN
  • Infinity - -Infinity,返回Infinity
  • -Infinity - Infinity,返回-Infinity
  • +0 - +0,返回+0
  • -0 - -0,返回-0
  • +0 - -0,返回-0
  • 有一个不是数值则调用Number()规则转为数值再应用上面规则
关系操作符规则
  • 都是数值则比较大小
  • 都是字符串,则比较字符编码
  • 一个数值则另一个转换成数值再比较
  • NaN和任何比较都是false
== 操作符比较流程
  1. 如果有一个为bool则先把bool转为数值再比较
  2. 有一个是对象另一个不是,则调用对象valueOf,再比较
  3. null和undefined相等(undefined派生自null)
  4. 有一个是NaN,则==返回false,!=返回true
  5. 对象和对象比较,内存一样返回true否则返回false

条件语句

  • 条件语句先调用Boolean()将其他类型转为bool
  • for循环执行判断并走完循环体再执行后面的运算
  • for...in循环对象无序性,各执行环境输出顺序不一样
  • 熟悉break,continue,label
  • switch用的是===与case比较,不存在隐式转换

三个基本包装类型

Number,String,Boolean

const a = 'abc';
a.substring(1);

// 相当于下面

const a = 'abc';
const b = new String(a);
b.substring(1);
//删除b

延长作用域链

  • with语句,将代码作用域设定到特定的对象
with(location){
    // 局部环境找不到定义,就会去location找同名属性
    const hostName = hostName;
    const qs = search.substring(1);
    const url = href;
}
  • try-catch语句的catch块IE8及其之前catch捕获的错误对象catch外部可以访问到,现在已被修复

垃圾收集

  • 标记清除:垃圾收集器在运行的时候给存储在内存中的所有变量都加上标记(可以用任何标记方式),然后去掉环境中的变量以及被环境中的变量引用的变量的标记。而在此之后再被加上标记的标量被视为准备删除的变量,原因是环境中的变量已经无法访问到这些变量,最后完成清楚工作,销毁那些带标记的值并回收它们所占用的内存空间
  • 引用计数:跟踪记录每个值的被引用的次数,当某个值的被引用次数变为0,则垃圾收集器下次再运行时,就会释放那个引用次数为0的值所占用的内存,为了避免循环引用,用完记得赋值null

Array.prototype.sort

第一个参数位于第二个之前则返回负值,相等则返回0,否则返回1

const arr = [
    {id: 2,age: 4},
    {id: 1,age: 2},
    {id: 3,age: 4},
    {id: 2,age: 5},
    {id: 3,age: 3},
    {id: 1,age: 1},
]

arr.sort((a, b)=>{
    // id升序
    if(a.id > b.id) return 1;
    if(a.id < b.id) return -1;
    // age升序
    if(a.age > b.age) return 1;
    if(a.age < b.age) return -1;

    return 0;
})

console.log(arr)

// [
//     { id: 1, age: 1 },
//     { id: 1, age: 2 },
//     { id: 2, age: 4 },
//     { id: 2, age: 5 },
//     { id: 3, age: 3 },
//     { id: 3, age: 4 }
// ]

callee和caller

  • callee:一个指针,指向拥有该arguments对象的函数
function factorial(n){
    if(n <= 1) return 1;
    return n * arguments.callee(n - 1);
}
console.log(factorial(5))
  • caller:该属性保存着调用当前函数的函数的引用
function b(){
    a()
}
function a(){
    console.log(a.caller === b)
}

b()//true

对象

对象的访问器和数据属性

  • 访问器属性:get,set,configurable,enumerable
  • 数据属性:writable.value,configurable,enumerable

new操作符

  1. 创建一个新对象
  2. 将构造器函数的作用域赋给新对象,即this
  3. 返回对象

概念

  • prototype:每个函数都有prototype属性,这是一个指针,指向一个对象,该对象用途是包含可以由特定类型的所有实例共享的属性和方法
  • 闭包:有权访问一个函数作用域中的变量的函数,理解执行环境的创建及作用域链和活动对象
  • 作用域链:本质是一个指向变量对象的指针列表,它只引用但不实际包含变量对象
  • this:this对象是运行时基于函数的执行环境绑定的,在全局函数中,this等于window,当函数被作为某个对象的方法调用时,this等于那个对象,匿名函数的执行环境具有全局性,因此this通常指向window