ThinkChat2.0新版上线,更智能更精彩,支持会话、画图、阅读、搜索等,送10W Token,即刻开启你的AI之旅 广告
[TOC] >[success] # Symbol的一些构造方法 <br/> >[success] ## Symbol.hasInstance 1. 应用场景:判断`数据类型` ~~~ 以前我们想检索一个'数据'是'某种数据类型'都是用'typeof',如下: let arr = [] // 定义一个数组 console.log(typeof arr) // object 上面我们想要的是'Array'类型,但是结果却是'Object',这时候用'typeof'就不行了,这时候 用'Symbol.hasInstance'判断即可,用'instanceof'也可以。'ES6只是将instanceof作为Symbol.hasInstance的简写方法' let arr = [] // 定义一个数组 console.log(arr instanceof Array) // true 等同于下面代码 let arr = [] // 定义一个数组 console.log(Array[Symbol.hasInstance](arr)) // true ~~~ 2. 定义一个无实例的函数 ~~~ 2.1 首先定义一个'有实例的函数',看一下是什么样子的,下面的'obj1是Object1类的实例' function Object1(){ // 空函数 } Object1.prototype.test = function(){ console.log('啊啊啊') } let obj1 = new Object1() // 实例化对象 console.log(obj1 instanceof Object1) // 打印 true,证明obj1是Object1类的实例 console.log(Object1[Symbol.hasInstance](obj1)) // true 2.2 接下来定义一个'无实例的函数',下面的'obj2'实际上确实是'Object2'类的实例,在调用过 'Object.defineProperty()'方法之后,'instanceof '就会返回'false',证明'obj2'不是'Object2' 的实例。 function Object2(){ // 空函数 } Object.defineProperty(Object2, Symbol.hasInstance, { // 给MyObject对象定义一个熟悉名为'Symbol.hasInstance'的熟悉,值为一个函数 value: function(v){ return false } }) let obj2 = new Object2() // 实例化对象 console.log(obj2 instanceof Object2) // 打印 false,证明obj2不是Object2的实例 console.log(Object2[Symbol.hasInstance](obj2)) // false ~~~ 3. 通过值来检查是否为实例 ~~~ // 1. class类中应用的场景 class MyClass { static [Symbol.hasInstance](num) { // 静态方法(静态方法不需要实例化对象就可以使用, 例如MyClass[Symbol.hasInstance](4)) return num % 2 === 0 } [Symbol.hasInstance](num) { // 动态方法 return num % 2 === 0 } } console.log(1 instanceof MyClass); // false console.log(2 instanceof MyClass); // true console.log(2 instanceof new MyClass()); // true // 2. 对象中的应用场景 const obj = { [Symbol.hasInstance](num) { return num % 2 === 0 } } console.log(1 instanceof obj); // false ~~~ ~~~ 我们可以通过'Object.defineProperty'方法'改写一个不可写属性 所以其实可以'重写'所有'内建函数(如Date和Error)'默认的'Symbol.hasInstance'属性 ~~~ <br/> >[success] ## Symbol.isConcatSpreadable ~~~ 'Symbol.isConcatSpreadable'用来'配置'某'数组'作为'concat()'方法的参数时,是否'展开其数组'元素。 ~~~ 1. Symbol.isConcatSpreadable用法 ~~~ // 设置Symbol.isConcatSpreadable前 const alpha = ['a', 'b', 'c']; const numeric = [1, 2, 3]; let alphaNumeric = alpha.concat(numeric); console.log(alphaNumeric); // ["a", "b", "c", 1, 2, 3] // 设置Symbol.isConcatSpreadable后 numeric[Symbol.isConcatSpreadable] = false; // 收起数组 alphaNumeric = alpha.concat(numeric); console.log(alphaNumeric); // ["a", "b", "c", [1, 2, 3]] // 等同于下面的扩展运算符写法 let a = ['a', 'b', 'c'] let b = [1, 2, 3] let c = [...a, ...b] // 展开数组 console.log(c) // [ 'a', 'b', 'c', 1, 2, 3 ] let d = [...a, b] // 收起数组 console.log(d) // [ 'a', 'b', 'c', [ 1, 2, 3 ] ] ~~~