永平建设有限公司网站,同仁行业网站建设报价,建站服务器多少钱,汉阴网站建设ES6-类-Symbol 1.类 在javascript语言中#xff0c;生成实例对象使用构造函数#xff1b;ES6提供了类Class这个概念#xff0c;作为对象的模板。定义一个类通过class关键字#xff0c;ES6的类可以看成是构造函数的另一种写法。 ES5 如何继承
实例使用属性和方法1.从实例对象…ES6-类-Symbol 1.类 在javascript语言中生成实例对象使用构造函数ES6提供了类Class这个概念作为对象的模板。定义一个类通过class关键字ES6的类可以看成是构造函数的另一种写法。 ES5 如何继承
实例使用属性和方法1.从实例对象本身查找属性或者方法2.如果实例没有从构造函数的原型对象中找3.如果还没有从父构造函数的原型对象中找function Person(){}
Person.prototype{};
var p1new Person();
p1.sayNamefunction(){};
p1.sayName(); //p1去调用sayName自身有访问自身自身没有访问构造函数原型对象构造函数原型对象没有去找父构造函数1.经典继承
function Animal(type,age,weight,length){this.typetype;this.ageage;this.weightweight;this.lengthlength
}
Animal.prototype{constructor:Animal,sayType:function(){console.log(this.type)}
}function Dog(type,age,weight,length,name,color){// 经典继承又称为构造函数继承Animal.call(this,type,age,weight,length);this.namename;this.colorcolor;
}
处理完构造函数处理原型对象
2.//原型链继承
Dog.prototypenew Animal();
Dog.prototype.constructorDog;
Dog.prototype.sayColorfunction(){console.log(this.color)
}
var d1new Dog(狗,1,10kg,40cm,可乐,白色);
console.log(d1);
d1.sayType();
d1.sayColor();ES6
1.如何定义一个类
class Person{constructor(name,age){this.namename;this.ageage}sayName(){ //--类似于存在类的原型对象中console.log(this.name)}
}
2.constructor方法是类的默认方法通过new命令生成对象实例时自动调用该方法。一个类必须有constructor方法如果没有显式定义一个空的constructor方法会被默认添加。通过static关键字来定义静态属性和静态方法。
class Person{ } class Person{constructor(){}}
3.定义在类体的方法称为实例方法,其实是存在于Person.prototype中可供所有的实例调用。
class Person{constructor(name,age){this.namename;his.ageage}sayName(){ //--- 其实可以理解为存在于Person.prototype中console.log(this.name)}
}
4.静态方法通过static关键字来定义静态属性和静态方法。也可以在外侧添加静态属性静态属性和静态方法是定义在类【构造函数】上的所以可以通过类【构造函数】直接访问。在静态方法中this指向当前类【构造函数】class Person{//静态属性是构造函数私有属性 并不是公共属性static test[hello];//可以是引用数据类型static test1hello;//可以是基本数据类型test3[];---实例私有属性//静态方法static sayName(){return this.test3}}class Person{//构造器 默认有一个可以显式提供constructor(name,age){// 实例的私有属性this.namename;this.ageage;}test[hello]// 实例的方法 原型对象中的方法sayName(){console.log(this.name)}// 静态方法static sayType(p){return p instanceof Person}//静态属性static gende男
};
let pnew Person(zhangsan,12);
let p2new Person({});
p.test.push(tom)
console.log(p,p2);//维护的是私有属性 创建的是不同子类构造函数对象
p.sayName();
console.log(Person.sayType(p));//静态方法由类去调用
console.log(p.testp2.test);//私有属性不相同
console.log(p.sayNamep2.sayName)//存放在原型对象中的是同一个方法实例方法和实例属性写在哪实例可以调用的方法和属性
静态方法和静态属性写在哪类本身调用的方法和属性2.继承 class可以通过extends关键字实现继承子类可以没有构造函数系统会默认分配。子类提供了构造函数则必须要显式调用super。super函数类似于借用构造函数。类似于Animal.call() 1.子类对象指向父类对象 2.子类原型对象继承父类原型对象 class Animal{// 静态属性static animalAttrAnimal的静态属性;constructor(name,age,weight){this.namename;this.ageage;this.weightweight;}// 实例方法sayName(){console.log(实例方法)}// 静态方法static animalmethod(){console.log(Animal静态方法)}
}
// 要实现继承
class Dog extends Animal{constructor(name,age,weight,color){super(name,age,weight);this.colorcolor;console.log(Dog的构造器)}
}
let dognew Dog(豆豆,1,10,golden);
// 继承 子类的原型对象继承父类的原型对象
dog.sayName();
// 继承 子类的对象通过__proto__指针指向父类的对象
Dog.animalmethod();
console.log(Dog.animalAttr);
console.log(Dog.__proto__Animal);
console.log(Dog.prototype.__proto__Animal.prototype)3.Symbol ES6引入的一种新的原始数据类型Symbol表示独一无二的值。Symbol函数可以接受参数表示对于这个唯一值的描述。属于基本数据类型,Symbol()函数会返回symbol类型的值 // 创建symbol值
let sy1Symbol(hello);
let sy2Symbol();
console.log(sy1sy2);
###1. 为了解决冲突
let obj{name:zhangsan,age:12
}
// 新增属性 修改属性
let sy3Symbol(name);
let obj1{...obj,// 属性名是变量名时使用中括号[sy3]:myname
}
console.log(obj1)
案例:
let sy1Symbol(age);
let sy2Symbol(name);
let obj{name:zhangsan,age:12,[sy1]:myname,[sy2]:myage,[Symbol(email)]:kangjiebriup.com
}
for(let key in obj){console.log(key);
}
let ssObject.getOwnPropertySymbols(obj);
console.log(obj[ss[2]]);### 2.消除魔术字符串魔术字符串指的是在代码之中多次出现、与代码形成强耦合的某一个具体的字符串或者数值。function test(shape,options){let area0;switch(shape){case Shape.SJX:area.5 * options.width*options.heightbreak;case Shape.ZFX:areaoptions.width*options.heightbreak;case Shape.CIRCLE:areaMath.PI*Math.pow(options.r,2)break;default:area-1 }return area
}
let Shape{SJX:Symbol(sjx),ZFX:Symbol(zfx),CIRCLE:Symbol(circle)
}
let restest(Shape.SJX,{width:100,height:100,r:100});
console.log(res);### 3.全局注册表
Symbol() 不同的是用 Symbol.for() 方法创建的的 symbol 会被放入一个全局 symbol 注册表中。Symbol.for() 并不是每次都会创建一个新的 symbol它会首先检查给定的 key 是否已经在注册表中了。假如是则会直接返回上次存储的那个。否则它会再新建一个。// 将symbol放到全局注册表中
let sy1Symbol.for(hello);
// 从全局注册表中找到该key对应的value
let sy2Symbol.for(hello);
console.log(sy1sy2);//true
// 每次都会创建一个不同symbol值 虽然描述符一样 但是Symbol value值不一样
let sy3Symbol(hello);
let sy4Symbol(hello);
console.log(sy3sy4);//falseSymbol.keyFor()
// Symbol.keyFor()可以检测symbol值是否在全局注册表中注册过。 返回对于symbol的描述或者undefined
let sy1Symbol.for(hello);
console.log(Symbol.keyFor(sy1));
let sy2Symbol(world);
console.log(Symbol.keyFor(sy2)) 1.迭代器 迭代器Iterator就是这样一种机制。它是一种接口为各种不同的数据结构提供统一的访问机制。任何数据结构只要部署Iterator接口就可以完成遍历操作即依次处理该数据结构的所有成员 Iterator 的作用有三个一是为各种数据结构提供一个统一的、简便的访问接口二是使得数据结构的成员能够按某种次序排列三是ES6创造了一种新的遍历命令for…of循环Iterator接口主要供for…of消费。 Iterator 的遍历过程是这样的。 创建一个指针对象指向当前数据结构的起始位置。也就是说遍历器对象本质上就是一个指针对象。 第一次调用指针对象的next方法可以将指针指向数据结构的第一个成员。 第二次调用指针对象的next方法指针就指向数据结构的第二个成员。 不断调用指针对象的next方法直到它指向数据结构的结束位置。 1.迭代器实现了Iterator接口,只要有实现了Iterator就可以使用for-of遍历
let arr[1,2,3,4,5];
console.log(arr.keys());
console.log(arr.values());
console.log(arr.entries());
// keys values entries 当前变量是迭代器对象
// 迭代器对象实现了Iterator接口只要实现了迭代接口就可以使用for-of 遍历
// let [a,b]10; 报错10 is not iterable
let strhello; //实现了迭代器接口,可以遍历
// console.log(a,b);
for(let key of str){console.log(key)
}
// 以前遍历字符串
let [...a]str;
console.log(a)
let resultstr.split()
console.log(result);
for(i0;istr.length;i){console.log(str.charAt(i))
}遍历迭代器对象
let keysarr.keys()
for(let key of keys){console.log(key)
}
let valuesarr.values();
for(let value of values){console.log(value,--------)
}
let entriesarr.entries();
for(let entry of entries){console.log(entry)
}
while(!(resultkeys.next()).done){console.log(result)
}
for-of实现原理就是调用迭代器的next()方法,第一次调用将指针指向数据结构的第一个成员依次调用依次指向直到没有成员可以指向done为true迭代过程:创建一个指针对象指向当前的数据结构起始位置;第一次调用指针对象的next方法指向数据结构的第一个成员第二次调用指针对象的next方法指向数据结构的第二个成员;直到done为true指向数据结构的结束位置;
let keysarr.keys();
let valuesarr.values();
let entriesarr.entries()
console.log(keys.next())
console.log(keys.next())
console.log(keys.next())
console.log(keys.next())
console.log(keys.next())
console.log(keys.next())
console.log(entries.next())原生具备 Iterator 接口的数据结构如下Array、Map、Set、String、TypedArray、arguments、NodeList 2.Set Set类似于数组但是成员的值都是唯一的没有重复的值。Set 本身是一个构造函数用来生成 Set 数据结构。Set 构造函数可以接受一个数组或者具有 iterable 接口的其他数据结构作为参数用来初始化。 Set API
var setnew Set()
//创建Set集合 成员是唯一的key-value是一样的
//添加元素
set.add(hello);
set.add(world);
set.add(world);
console.log(set);
// 删除元素
set.delete(hello);
console.log(set);
// 遍历
let keysset.keys()
let valuesset.values()
let entriesset.entries();
console.log(keys,values,entries);
set.forEach((value){console.log(value)
})
//判断有没有某个成员
set.has(hello);返回布尔值true或者false
//清空set
set.clear();
//返回set成员个数
set.size
------------------------------------------------
set应用 set构造函数可以接受数组或者其他可遍历的数据结构
let setnew Set([1,2,3,4,1,2,3,4]);
console.log(set);
//数组去重
let arr[1,2,3,5,3,2];
let resultnew Set(arr);
console.log(result);
//将字符串转换为数组
let [...arr1]hello;
//将set集合转换为数组
let [...arr2]result;
console.log(arr2);console.log([...new Set(arr)])let s new Set();
s.add([1]);
s.add([1]);
console.log(s);
console.log(s.size);3.Map集合 Map类似于对象也是键值对的集合但是“键”的范围不限于字符串各种类型的值包括对象都可以当作键。也就是说Object 结构提供了“字符串—值”的对应Map结构提供了“值—值”的对应是一种更完善的 Hash 结构实现。如果你需要“键值对”的数据结构Map 比 Object 更合适。Map 可以接受一个数组作为参数。该数组的成员是一个个表示键值对的数组。 let obj{name:zhangsan,age:12
}
//遍历键值对组成的数组
let arrObject.entries(obj);
console.log(arr);
//将数组作为参数放到Map中
let mapnew Map(arr)
console.log(map);// 添加元素
map.set(1,1);
console.log(map);
// 删除元素
map.delete(name);
console.log(map);
// 获取元素
console.log(map.get(age));
// 遍历
let keysmap.keys()
let valuesmap.values()
let entriesmap.entries();
console.log(keys,values,entries);
map.forEach((value,key){console.log(value,key)
})
MapObject意外的键Map 默认情况不包含任何键。只包含显式插入的键。一个 Object 有一个原型, 原型链上的键名有可能和你自己在对象上的设置的键名产生冲突。键的类型一个 Map的键可以是任意值包括函数、对象或任意基本类型。一个Object 的键必须是一个 String 或是Symbol。键的顺序Map 中的 key 是有序的。因此当迭代的时候一个 Map 对象以插入的顺序返回键值。一个 Object 的键是无序的。注意自ECMAScript 2015规范以来对象确实保留了字符串和Symbol键的创建顺序 因此在只有字符串键的对象上进行迭代将按插入顺序产生键。SizeMap 的键值对个数可以轻易地通过size 属性获取Object 的键值对个数只能手动计算迭代Map 是 iterable 的所以可以直接被迭代。迭代一个Object需要以某种方式获取它的键然后才能迭代。性能在频繁增删键值对的场景下表现更好。在频繁添加和删除键值对的场景下未作出优化。 4.数值扩展 Number.isFinite(), Number.isNaN()
与isFinite、isNaN不同这两个新方法只对数值有效Number.isFinite()对于非数值一律返回false, Number.isNaN()只有对于NaN才返回true非NaN一律返回false。 Number.isFinite(0.8); // trueNumber.isFinite(NaN); // falseNumber.isFinite(Infinity); // falseNumber.isNaN(NaN) // trueNumber.isNaN(15) // falseNumber.parseInt(), Number.parseFloat()
ES6 将全局方法parseInt()和parseFloat()移植到Number对象上面行为完全保持不变。
Number.parseInt(12.34) // 12
Number.parseFloat(123.45#) // 123.45Number.isInteger()
Number.isInteger()用来判断一个数值是否为整数。
Number.isInteger(25) // true
Number.isInteger(25.1) // falseasync异步函数 async函数是使用async关键字声明的函数。 async函数是AsyncFunction构造函数的实例 并且其中允许使用await关键字。async和await关键字让我们可以用一种更简洁的方式写出基于Promise的异步行为而无需刻意地链式调用promise。 await关键字只在async函数内有效。如果你在async函数体之外使用它就会抛出语法错误 SyntaxError 。async/await的目的为了简化使用基于promise的API时所需的语法。async/await的行为就好像搭配使用了生成器和promise。async函数一定会返回一个promise对象。如果一个async函数的返回值看起来不是promise那么它将会被隐式地包装在一个promise中。 简单来说 是一个函数是一个异步编程解决方案内部封装了generator函数是一个语法糖内部自带执行器与await配合使用异步编程同步处理; async function loadArticle() {try {let res await axios.get(http://122.199.0.35:8888/index/category/findAll)console.log(res.data.data);} catch(error) {throw new Error(请求失败);} finally {console.log(最终执行);}}
loadArticle()forEach、for in、for of三者区别forEach更多的用来遍历数组for in 一般常用来遍历对象或数组for of遍历实现了迭代器接口的对象遍历对象需要通过Object.keys()