变量
ES6中增加了let和const用来声明变量
- var声明的变量可以重复声明、无法限制修改、没有if/for等块级作用域,只有函数作用域
- let声明的变量不能重复声明,变量可以修改,块级作用域
- const声明的常量不能重复声明,常量不允许修改,块级作用域
函数
箭头函数
ES6中增加了箭头函数,类似于lambda表达式 箭头函数里面的this指向上下文
- 如果只有一个参数,()可以省略
- 如果只有一个返回值,{}可以省略
箭头函数示例:
// 原来的写法window.onload = function () {alert('abc');};// 箭头函数写法window.onload = ()=>{alert('abc');};// 原来的带参数函数写法let show = function(a,b){alert(a + b);};// 箭头函数的带参数写法let show = (a,b)=>{alert(a,b);};// 例如数组排序// 原来写法let arr = [12,5,6,4,22,8,10];arr.sort(funtion (n1, n2){return n1 - n2;});// 箭头函数写法let arr = [12,5,6,4,22,8,10];arr.sort((n1, n2)=>{return n1 - n2;});// 只有一个参数时小括号可以省略,只有一个return时大括号可以省略let show = funtion(a) {return a*2;};let show = a=>a*2;
函数的参数
参数的扩展/数组展开; 默认参数
参数扩展
收集剩余的参数```javascript function show(a, b, …args) { // ….除了a,b之外,函数的其余参数全部存放在args数组中
// 存放剩余参数的变量Rest Parameter必须为最后一个参数,后面不能再有其他参数
} ```
展开数组```javascript let arr = [1,2,3]; function show(a, b, c) { // ….. } show(…arr); // 将arr数组展开,对应到show的参数,等价于show(1,2,3)
// 将arr1、arr2数组中的值存入arr3数组中 // 数组展开后的效果,和直接把数组内容写在这里一样 let arr1 = [1,2,3]; let arr2 = [4,5,6]; let arr3 = […arr1, …arr2];
<a name="2171d1b0"></a>#### 默认参数```javascriptfunction show(a, b=5, c=12){console.log(a, b, c);}show(99);
解构赋值
- 左右两边结构必须一样
- 右边必须是个东西
- 声明和赋值不能分开(必须在一句话里完成)
// 原来的写法let arr = [1,2,3];let a = arr[0];let b = arr[1];let c = arr[2];// 解构赋值写法let [a, b, c] = arr;// JSON解构赋值,找json中对应名称的值,左右两边的结构同时为jsonlet testJson = {a:1,b:2,c:3,d:4};let {a, c} = testJson;// 解构赋值时,左右两边必须结构一致let [{a,b}, [n1, n2, n3], d, e] = [{a:1, b:2, c:3}, [4, 5, 6], 7, 'aaa'];// 可以解析成任意粒度let [testJson, [n1, n2, n3], d, e] = [{a:1, b:2, c:3}, [4, 5, 6], 7, 'aaa'];// 可以在数组、json中使用...语法创建剩余变量数组let [first, ...rest] = [1, 2, 3, 4];// 仅赋值某几个变量let [ , second, , fourth] = [1, 2, 3, 4];
数组
map:一个对一个的进行映射 reduce:汇总,进来一堆,返回一个。 filter:过滤,通过返回值true或false决定是否保留 forEach:循环迭代
// map示例// 返回数组对应每个分值是否及格let arr = [55,20,66,42,80,11,100];let result = arr.map(item => item>=60?'及格':'不及格');// reduce示例// 求最大值let arr = [12,5,6,49,23,42,55,14,35];// 循环 两两运算,tmp为中间结果,item为数组每项值,index为计算次数var result = arr.reduce(function (tmp, item, index) {return tmp > item ? tmp:item;});// 求平均值let arr = [12,5,6,49,23,42,55,14,35];// 循环 两两运算,tmp为中间结果,item为数组每项值,index为计算次数var result = arr.reduce(function (tmp, item, index) {if(index == arr.length-1) {return (tmp+item)/arr.length;}else{return tmp+item;}});// filter示例// 返回只含有被3整除的数字的数组let arr = [12,5,6,49,23,42,55,14,35];var result = arr.filter(item => item%3==0);// forEeach示例// forEach可以有一个参数item,也可以有两个参数index,itemlet arr = [12,5,6,49,23,42,55,14,35];arr.forEach(item => alert(item));
字符串
- 多了两个新方法
- startsWith
- endsWith
- 字符串模板
- 直接把东西塞到字符串里面:$(东西)
- 字符串中可以换行
// 以前的写法let title = '标题';let content = '内容';let str = '<div>\<h1>' + title + '</h1>\<p>' + content + '</p>\</div>';// 字符串模板写法let title = '标题';let content = '内容';let str = `<div><h1>${title}</h1><p>${content}</p></div>`;
面向对象
- 多了class关键字,使得构造器和类分开
- class里面直接加方法
原来的js类写法:
// User既是类,又是构造方法,两者未分开function User(name, pass) {this.name = name;this.pass = pass;// 在构造方法中为类添加函数this.show=function (){alert(this.name + ' is ' + this.pass);}}// 使用原型链为类添加属性User.prototype.sex = '男';// 使用原型链为类增加函数User.prototype.showName = function (){alert(this.name);};User.prototype.showPass = function () {alert(this.pass);};// 静态属性User.level = 1;// 静态方法User.getInfo = function (){alert('静态方法');}// 调用静态方法User.getInfo();// 实例化对象调用var u1 = new User('zhangsan', '123456');u1.showName();u1.showPass();// 继承 (构造函数对象冒充 + 原型链 组合继承)function VipUser(name, pass, level) {// 单独用对象冒充可以继承构造函数里面的属性和方法,但是没法继承原型链上的属性和方法User.call(this, name, pass); // 使用call获取父类的构造方法(对象冒充实现继承)this.level = level;}// 原型链实现继承(单独用原型链继承,可以继承构造函数里面的属性和方法,也可以继承原型链上的属性和方法)// 但是单独用原型链实现的继承,在实例化子类的时候,没法给对象传参VipUser.prototype = new User(); // 将User的方法继承到VipUser原型上VipUser.prototype.constructor = VipUser; // 再将VipUser的构造方法还原成VipUser本身的构造方法VipUser.prototype.showLevel = function () {alert(this.level);}var v1 = new VipUser('testVip', '123456', 12);v1.showName();v1.showPass();v1.showLevel();
ES6的类写法:
class User{constructor(name, pass) {this.name = name;this.pass = pass;}showName() {alert(this.name);}showPass() {alert(this.pass);}}var u1 = new User('zhangsan', '123456');u1.showName();u1.showPass();// 继承class VipUser extends User{constructor(name, pass, level) {super(name, pass);this.level = level;}showLevel(){alert(this.level);}}
面向对象在React框架中的应用
react框架: 1.组件化—-class; 2.JSX(JSX == babel == browser.js)
JSON
json标准写法
- 只能用双引号
- 所有的名字都必须用引号包起来
- JSON对象
- JSON.stringify
- JSON.parse
- 简写
- 名字和值(key和value)一样的,留一个就行
- 方法,冒号和function关键字一起省略
```javascript
// 原来的写法
var a = 1;
var b = 2;
var testJson = {“a”: a,
"b": b,"c": 120,show : function (){// .....}};
// 简写
// key的双引号可以省略
let testJson = {a:a , b:b, c: 120}
// 名称和值变量相同的,只需留一个
let testJson = {a, b, c:120}
// 函数的冒号和function关键字可以省略
let testJson = {
show(){
//…
}
}
<a name="Promise"></a>## Promise> 异步:操作之间没有关系,同时进行多个操作。> 同步:同时只能做一件事。> 异步:代码更复杂。> 同步:代码简单原始的同步异步代码,例如:```javascript// 异步ajax("/banners", function(banner_data){ajax("/hotItems", function(hotItems_data){ajax("/slides", function(slides_data){//....},function(){alert('读取失败');});},function(){alert('读取失败');});},function(){alert('读取失败');});// 同步let banner_data = ajax_async('/banners');let hotItem_data = ajax_async('/hotItems');let slide_data = ajax_async('/slides');
Promise : 消除异步操作
用同步一样的方式,来书写异步代码
Promise中存放单一的ajax示例:
// new一个Promise对象let p = new Promise(function (resolve, reject){// 异步代码// resolve -- 成功了// reject -- 失败了$.ajax({url: "arr.txt",dataType: 'json',success(arr){resolve(arr);},error(err){reject(err);}});});// 当Promise执行有结果时,调用then// then的参数中,第一个函数为成功时执行的函数,即resolve()// then的参数中,第二个函数为失败时执行的函数,即reject()p.then(function(arr) {alert('成功' + arr);}, function(err) {alert('失败' + err);});
Promise中存放多个ajax示例:
// 第一个ajaxlet p1 = new Promise(function(resolve, reject){$.ajax({url:'arr.txt',dataType:'json',success(arr){resolve(arr);},error(err){reject(err);}});});// 第2个ajaxlet p2 = new Promise(function(resolve, reject){$.ajax({url:'testJson.txt',dataType:'json',success(testJson){resolve(testJson);},error(err){reject(err);}});});// 当所有的Promise都成功时,执行thenPromise.all([p1,p2]).then(function(arr){// 成功后的arr为一个数组,数组中每项值为对应前面的Promise对象的结果let [result1, result2] = arr;alert("全都成功了");alert("p1的结果为" + result1);alert("p2的结果为" + result2)}, function(err){alert("至少一个失败了");});
对上面示例进行封装:
function createPromise(url){return new Promise(function(resolve, reject){$.ajax({url,dataType:'json',success(testJson){resolve(testJson);},error(err){reject(err);}});}Promise.all([createPromise('arr.txt');createPromise('testJson.txt');]).then(function(arr){let [result1, result2] = arr;alert("全都成功了");alert("p1的结果为" + result1);alert("p2的结果为" + result2)}, function(err){alert("至少一个失败了");});
Jquery本身带有的Promise
// jQuery的ajax返回值就是一个Promise对象let p = $.ajax(url:'arr.txt', dataType:json);// 所以,Jquery的ajax可以直接写在Promise的all数组中Promise.all([$.ajax(url:'arr.txt', dataType:json);$.ajax(url:'testJson.txt', dataType:json);]).then(function(arr){let [result1, result2] = arr;alert("全都成功了");alert("p1的结果为" + result1);alert("p2的结果为" + result2)}, function(err){alert("至少一个失败了");});
Promise的其他方法:
// Promise.race,哪个执行的最快,就返回哪个结果,不管结果本身是成功状态还是失败状态Promise.race([$.ajax(url:'arr.txt', dataType:json);$.ajax(url:'testJson.txt', dataType:json);]).then(function(arr){alert("成功了" + result1);}, function(err){alert("失败了");});
generator
generator是一种特殊的函数。 普通函数—-执行时一路执行到底; generator函数——执行的过程中间可以暂停
// generator函数写法:function和函数名之间加星号// 可以写为 function* show(){...}; function *show(){...}; function * show(){...};// 不能写为 function*show(){...}// 不能写为箭头函数 *show()=>{....}function *show(){alert(1);alert(2);yield; // 使用yield关键字,放弃运行状态,运行到这里就停止alert(3);alert(4);}// 直接调用show()不会执行,返回一个generator对象let genObj1 = show();// next()执行到yield就停止genObj1.next();// yield暂停期间,可以执行其他代码alert(5);// 再次调用next()继续执行genObj1.next();
yield可以传参
// 定义函数时,可以选择有参数函数function *show(num1, num2) {alert(`${num1},${num2}`);alert(1);// yield和上面的代码一起执行,然后暂停,下次next时传入的参数222返回给alet a = yield;alert(a);alert(2);}let genObj = show(1, 2); // 给函数传入参数num1,num2genObj.next(111); // 此处传入的111没有任何作用alert(5);genObj.next(222); // 此处传入的222将作为yield值,传递给let a
yield可以return
function *show(){alert(1);yield 12;alert(2);return 55;}let genObj = show();let res1 = genObj.next(); // 可以获取到当前yield的返回值console.log(res1); // JSON类型:{value:12, done:false}let res2 = genObj.next(); // 最后一次的值是通过return获取console.log(res2); // JSON类型: {value:55, done:true}
yield传参和返回,伪代码示例:
function *炒菜 (菜市场买回来的原材料){// ... 洗菜yield '洗好的菜';// ...切菜let 配料 = yield '切好的菜';// ...炒菜return '炒熟的菜';}let genObj = 炒菜();let res1 = genObj.next(); // 获取到'洗好的菜'。炒菜过程未完成,done=false// ...调制配料let res2 = genObj.next(); // 获取到'切好的菜'let res3 = genObj.next('配料'); // 将'配料'传进炒菜过程,最终获取到'炒熟的菜',炒菜过程完成,done=true
可以使用generator函数编写异步操作,类似Promise。
Promise适合场景:Promise中的所有异步ajax都需要读,一次读一堆;
generator适合场景:generator中间需要很多逻辑判断,后续操作需要根据前面的结果有条件操作;
ES7&8预览功能
数组
多了includes方法:数组是否包含某个东西
javascript let arr = [12,5,8]; alert(arr.includes(12));keys/values/entries> keys:所有的key;
values:所有的value; entries:所有的实体(即键值对)
for…of循环:循环iterator迭代器
for—-in循环:循环数组、JSON```javascript
let arr = [12,5,8,32];
// for…in循环
for(let i in arr){
alert(i); // alert的i为arr的key:0,1,2,3,
}
// for…of循环
for(let i of arr) {
alert(i); // alert的i为arr的value:12,5,8,32
}
// json遍历
let testJson = {a: 12, b: 5, c:8};
for(let i in testJson) {
alert(i); // alert的i为json的key:a,b,c
}
// JSON不是可迭代对象,不能使用for…of循环
for(let i of testJson) {
alert(i);
}
```javascriptlet arr = [12, 5, 8, 22];// 使用for..of遍历arr的keyfor(let i of arr.keys()) {alert(i);}// 使用for...of遍历arr的valuefor(let i of arr.values()) {alert(i);}// 使用for...of遍历arr的键值对for(let [key,value] of arr.entries()) {alert(`${key}=${value}`);}
幂
使用**来进行幂次运算
alert('2的3次方=' (2**3));
字符串
ES7的字符串新增加了两个方法:
- padStart:左边补齐多少位
- padEnd:右边补齐多少位
alert('abc'.padStart(5)); // 左边补2个空格凑足5位长度alert('123'.padStart(5,'0')); // 左边补2个0凑足5位长度alert('123'.padStart(5,'0')); // 右边补2个0凑足5位长度
语法容忍度
某些“错误”的语法正常执行
数组语法容忍
javascript // ES6功能,数组最后多了一个逗号,依然可以正常执行 let arr = [12, 5, 8, 6, ];函数参数语法容忍
javascript // ES7功能,函数参数最后多了一个逗号,依然可以正常执行 function show(num1, num2, ){ //... }
async和awaite
用来替代generator yield。 原来的generator会被封装一个runner进行执行,async不再依赖外部的runner。 async 可以写成箭头函数。
// 原来的generator的runner写法runner(function *readData(){let data1 = yield $.ajax({url: 'data/1.txt', dataType: 'json'});let data2 = yield $.ajax({url: 'data/2.txt', dataType: 'json'});let data2 = yield $.ajax({url: 'data/3.txt', dataType: 'json'});console.log(data1,data2,data3);});// async写法async function readData(){let data1 = await $.ajax({url: 'data/1.txt', dataType: 'json'});let data2 = await $.ajax({url: 'data/1.txt', dataType: 'json'});let data3 = await $.ajax({url: 'data/1.txt', dataType: 'json'});console.log(data1, data2, data3);}readData();//async的箭头函数写法let readData = async ()=>{//...}
