本系列博客为ES6基础语法的使用及总结,如有错误,欢迎指正。
重学ES6之出来混迟早要还的(四)主要包括Array.from()、Array.of()、find()/findIndex()、some()/every()、Promise、ES6对象增强写法。
Array.from()/Array.of()
这两个方法不是原型上面的方法,直接使用会报错
let arr = [1,2,3];
console.log(arr.from());
//Uncaught TypeError: arr.from is not a function
console.log(arr.of());
//Uncaught TypeError: arr.of is not a function
Array.from()
1.用法
用于把一个类数组对象或者是一个可遍历对象转换为一个真正的数组
类数组对象是啥?
具有索引属性(数字),有length属性的对象;比如NodeList对象
可遍历对象是啥?
别问,问就是让你去看前面两篇笔记
(1) 格式:Array.from(arrayLike[, mapFn[, thisArg]])
(2) 参数:
- arrayLike 想要转换成数组的伪数组对象或可迭代对象。
- mapFn 可选 如果指定了该参数,新数组中的每个元素会执行该回调函数。
- thisArg 可选 执行回调函数 mapFn 时 this 对象。
(3) 返回值:一个新的数组实例。
(4) 示例
// 从String生成数组
Array.from('foo');
// [ "f", "o", "o" ]
console.log(Array.from([1, 2, 3], x => x + x));
// expected output: Array [2, 4, 6]
Array.from(obj, mapFn, thisArg)
的格式相当于 Array.from(obj).map(mapFn, thisArg)
let oLis = document.querySelectorAll('li');
let num = Array.from(oLis).map(li => li.innerHTML);
console.log(num); //["1", "2", "3"]
//等价于
let liArr = Array.from(oLis,li => li.innerHTML);
console.log(liArr); //["1", "2", "3"]
2.应用场景
-
可以将函数里面的arguments对象转换为数组,多嘴一句:在这篇里面也说了剩余参数也可以将函数参数打包为一个数组。
function list(...numbers) { console.log(numbers); } list(1,2,3,4,5); function list2() { console.log(Array.from(arguments)); } list2(6,7,8,9,10);
-
将字符串转为字符串数组
let arr = Array.from('ridiculous'); console.log(arr); //["r", "i", "d", "i", "c", "u", "l", "o", "u", "s"] let str = 'ridiculous'; let arr2 = str.split(''); console.log(arr2); //["r", "i", "d", "i", "c", "u", "l", "o", "u", "s"]
Array.of()
1.用法Array.of()
方法创建一个具有可变数量参数的新数组实例,而不考虑参数的数量或类型。
Array.of()
和 Array
构造函数之间的区别在于处理整数参数:Array.of(7)
创建一个具有单个元素为7的数组(注意:数组的长度是1),Array(7)
创建一个长度为7的空数组(注意:这是指一个有7个空位(empty)的数组,而不是由7个undefined
组成的数组)。
let arr = Array(5);
console.log(arr); //[empty × 5] 是一个长度为5,数值都为空的数组
let arr2 = Array.of(5);
console.log(arr2); //[5] 是一个长度为1,元素值为5的数组
let arr = Array(0);
console.log(arr); //[]
let arr2 = Array.of(0);
console.log(arr2); //[0]
也就是说使用 Array.of()
能够保证传入的数据和返回结果的一致性,不管传入多少个参数,返回的是由这些元素组成的数组;弥补了Array()
构造函数的不足
let arr = Array(1,2,3);
console.log(arr); //[1,2,3]
let arr2 = Array.of(1,2,3);
console.log(arr2); //[1,2,3]
find()/findIndex()/some()/every()
find()
find() 方法返回数组中满足提供的测试函数的第一个元素的值。否则返回 undefined。
找到满足条件的第一个就会立即停止
1.用法
格式:arr.find(callback[, thisArg])
参数:① callback 在数组每一项上执行的函数,接收 3 个参数:
- element 当前遍历到的元素。
- index 可选 当前遍历到的索引。
- array 可选 数组本身。
② thisArg 可选 执行回调时用作this 的对象。
返回值:数组中第一个满足所提供测试函数的元素的值,都找不到否则返回 undefined。
let inventory = [
{name: 'apples', quantity: 2},
{name: 'bananas', quantity: 0},
{name: 'cherries', quantity: 5}
];
let cherry = inventory.find(fruit => fruit.name === 'cherries');
console.log(cherry); // { name: 'cherries', quantity: 5 }
findIndex()
findIndex()方法返回数组中满足提供的测试函数的第一个元素的索引。找不到则返回-1。
1.用法
格式:arr.findIndex(callback[, thisArg])
参数:① callback 针对数组中的每个元素, 都会执行该回调函数, 执行时会自动传入下面三个参数:
- element 当前元素。
- index 当前元素的索引。
- array 调用findIndex的数组。
② thisArg 可选。执行callback时作为this对象的值.
返回值:数组中通过提供测试函数的第一个元素的索引。否则,返回-1
let cherryIndex = inventory.findIndex(fruit => fruit.name === 'cherries');
console.log(cherryIndex); //2
some()
some() 方法测试数组中是不是至少有1个元素通过了被提供的函数测试。它返回的是一个Boolean类型的值。
找到满足条件的第一个就会立即停止
1.用法
格式:arr.some(callback(element[, index[, array]])[, thisArg])
参数: ① callback用来测试每个元素的函数,接受三个参数:
- element 数组中正在处理的元素。
- index 可选 数组中正在处理的元素的索引值。
- array 可选 some()被调用的数组。
② thisArg可选
执行 callback 时使用的 this 值。
返回值:数组中有至少一个元素通过回调函数的测试就会返回true;所有元素都没有通过回调函数的测试返回值才会为false。
let isZero = inventory.some(fruit => fruit.quantity === 0);
console.log(isZero); //true
every()
every() 方法测试一个数组内的所有元素是否都能通过某个指定函数的测试。它返回一个布尔值。
如果有一个为false,则立即返回false,后面的不再执行
1.用法
格式:arr.every(callback[, thisArg])
参数:① callback 用来测试每个元素的函数,它可以接收三个参数:
- element 用于测试的当前值。
- index 可选 用于测试的当前值的索引。
- array 可选 调用 every 的当前数组。
② thisArg 执行 callback时使用的 this
值。
返回值:如果回调函数的每一次返回都为 truthy 值,返回 true ,否则返回 false。
let allZero = inventory.every(fruits => fruits.quantity === 0);
console.log(allZero); //false
Promise
官方说法之又臭又长不看版:
Promise 对象用于表示一个异步操作的最终完成 (或失败), 及其结果值.Promise构造函数执行时立即调用
executor
函数,resolve
和reject
两个函数作为参数传递给executor
(executor 函数在Promise构造函数返回所建promise实例对象前被调用)。resolve
和reject
函数被调用时,分别将promise的状态改为fulfilled(完成)或rejected(失败)。executor 内部通常会执行一些异步操作,一旦异步操作执行完毕(可能成功/失败),要么调用resolve函数来将promise状态改成fulfilled,要么调用reject
函数将promise的状态改为rejected。如果在executor函数中抛出一个错误,那么该promise 状态为rejected。executor函数的返回值被忽略。
1.Promise基本概念
1.1 what
promise是ES6中新增的异步编程解决方案。简单说就是一个容器,里面保存着某个未来才会结束的事件的结果。
从语法上说,Promise 是一个对象,从它可以获取异步操作的消息。可以通过new Promise(function(resolve, reject)
来创建
1.2 why
通过Promise就可以实现:用同步的流程来表示异步的操作;解决回调顺序的不确定性,解决回调地狱的问题
1.3 how
Promise构造函数接受一个函数作为参数,该函数的两个参数分别是resolve
和reject
。它们是两个函数,由JavaScript引擎提供,不用自己部署。
resolve
函数的作用是,将Promise对象的状态从“未完成”变为“成功”(即从Pending
变为Resolved
),在异步操作成功时调用,并将异步操作的结果,作为参数传递出去;
reject
函数的作用是,将Promise对象的状态从“未完成”变为“失败”(即从Pending
变为Rejected
),在异步操作失败时调用,并将异步操作报出的错误,作为参数传递出去。
let p = new Promise(function(resolve, reject) {
// ... some code
if (/* 异步操作成功 */){
resolve(value);
} else {
reject(error);
}
});
2.Promise对象三种状态(面试必问)
- pending:默认状态,只要没有说明promise任务是成功还是失败就是pending状态
- fulfilled(resolved):只要调用resolve函数, 状态就会变为fulfilled, 表示操作成功
- rejected:只要调用rejected函数, 状态就会变为rejected, 表示操作失败
3.Promise 常用的方法有哪些?它们的作用是什么?
3.1 Promise.then
- Promise 实例具有then方法,也就是说,then方法是定义在原型对象Promise.prototype上的。
- 它的作用是为 Promise 实例添加状态改变时的回调函数。
- then方法的第一个参数是resolved状态的回调函数,第二个参数(可选)是rejected状态的回调函数。
3.2 Promise.catch
Promise.catch方法是.then(null, rejection)
或.then(undefined, rejection)
的语法糖,用于指定发生错误时的回调函数。
3.3 Promise.all
all方法接收一个数组,,当所有实例promise的结果都是成功时,才会执行后面then方法里面的内容
如果有一个promise实例的状态是失败的,那么就会执行catch方法
const userPromise = new Promise((resolve,reject) =>{
setTimeout(() => {
resolve(['lucy','lily','eli']);
},2000)
});
const moviePromise = new Promise((resolve,reject) => {
setTimeout(() => {
// resolve({name: '卡萨布兰卡',score: '9.8', published: '1964'});
reject('no movie found');
},500);
});
Promise.all([userPromise,moviePromise])
.then(response => {
console.log(response);
let [user,movie] = response;
console.log(user);
console.log(movie);
})
.catch(err => console.log(err));
已知userPromise
的状态已经确定了是成功的,所以all方法返回的内容取决于moviePromise
的状态:
如果moviePromise
的状态是成功,则all方法执行then里面的内容。正常打印response、user、movie
如果moviePromise
的状态是失败,则all方法执行catch里面的内容。抛出错误
3.4 Promise.race
race方法由数组里面第一个promise实例返回的状态决定,如果第一个promise返回的状态是成功,那么race方法执行then方法里面的内容;
如果第一个promise实例返回的状态是失败,则race方法执行catch方法里面的内容
const userPromise = new Promise((resolve,reject) =>{
setTimeout(() => {
resolve(['lucy','lily','eli']);
},2000)
});
const moviePromise = new Promise((resolve,reject) => {
setTimeout(() => {
resolve({name: '卡萨布兰卡',score: '9.8', published: '1964'});
// reject(Error('no movie found'));
},500);
});
Promise.race([userPromise,moviePromise])
.then(response => {
console.log(response);
})
.catch(err => console.log(err));
race方法执行的结果取决于先执行的moviePromise
返回的结果,
如果moviePromise
的状态是成功的,那么race方法执行then里面的内容。正常打印response
如果moviePromise
的状态是失败的,那么race方法执行执行catch里面的内容。抛出错误
4.Promise常见面试题
let promise = new Promise((resolve, reject)=>{
console.log('我是promise任务');
resolve('resolved')
})
promise.then(res =>{
console.log(res)
})
console.log("我是同步任务");
setTimeout(()=>{
console.log("我是延时任务");
}, 0)
答案:执行顺序:我是promise任务、我是同步任务、resolved、我是延时任务。
ES6对象增强写法
1.过去定义一个对象的写法
const obj = {
name: 'ghk',
age: 18,
gender: 'male',
greet: function ()
console.log(hello);
}
}
2.当一个对象的属性是从外面获取的时候,可以采用下面这种方式
const name = 'ghk';
const age = 18;
const gender = 'man';
const obj = {
name,
age,
gender,
getName(){
console.log(this.name);
}
};