剩余参数与展开运算符
剩余参数是什么
//1.剩余参数
//const add=(x,y,z,...args)=>{};
//2.剩余参数的本质
//剩余参数永远是一个数组,即使没有值,也是空数组
const add=(x,y,...args)=>{
console.log(x,y,args)
};
add(1,2,3,4,5)
//3,4,5->[3,4,5]
剩余参数的注意事项
1.箭头函数的剩余参数
2.使用剩余参数替代 arguments 获取实际参数
3.剩余参数的位置
/*1.箭头函数的参数部分即使只有一个剩余参数,也不能省略圆括号
const add=(...args)=>{};*/
/*2.
const add=function(){
console.log(arguments);
}; */
const add=(...args)=>{
console.log(args);
};
add(1,2);//(2) [1, 2]
/*3.剩余参数只能是最后一个参数,之后不能再有其他参数,否则会报错*/
剩余参数的应用 [重要]
/*1.完成 add 函数
//没有体现剩余参数作为数组的优势,使用数组的一些方法[reduce 方法],让程序更简单
const add=(...args)=>{
let sum=0;
for(let i=0;i<args.length;i++){
sum+=args[i];
}
return sum;
};
console.log(add(1,2,3))//6
*/
/*2.与解构赋值结合使用
剩余参数不一定非要作为函数参数使用
const [num,...args]=[1,2,3,4];
console.log(num,args);
//数组的解构赋值还可以和函数参数再结合使用
const func=([num,...args])=>{};
console.log(([1,2,3]))
//const func=(...args)=>{};...args 永远是一个真正的数组,没有值也是个空数组
//用在函数参数中的,叫真正的剩余参数
//剩余参数还可以和对象的解构赋值结合使用的 z(也可以是个对象)称为剩余元素 '剩余参数永远是个数组' 并不矛盾]
const {x,y,...z}={a:3,x:1,y:2,b:4};
console.log(x,y,z)
*/
/*3.对象的解构赋值同样和数组一样扔到函数中来*/
const func=({x,y,...z})=>{};
console.log({a:3,x:1,y:2,b:4})
数组展开运算符的基本用法
//1.认识展开运算符
//[3,1,2] 求最小的值 1 Math.min 不能接收数组,接收的参数列表形式
//解决: 将数组形式转换成参数列表形式 [3,1,2] -> 3,1,2
//2.数组展开运算符的基本用法
console.log(Math.min(...[3,1,2]));
区分剩余参数和展开运算符
const add=(...args)=>{
//剩余参数
console.log(args);
//展开运算符
console.log(...args);
}
console.log([...[1,2,3],4]);//[1,2,3,4]
数组展开运算符的应用 [重要]
/*1.复制数组
const c=[...a];
console.log(c);
*/
/*这不叫复制
const a=[1,2];
const b=a;
a[0]=3;
console.log(b);//[3,2]
*/
/*2.合并数组
const a = [1, 2];
const b = [3];
const c = [4, 5];
console.log([...a, ...b, ...c]); //[1, 2, 3, 4, 5]
console.log([1,...b,2,...a,...c,3]);//[1, 3, 2, 1, 2, 4, 5, 3]
*/
/*3.字符串转为数组
字符串可以按照数组的形式展开
console.log([...'alex']);//['a', 'l', 'e', 'x']
console.log('alex'.split(''));
*/
/*4.常见的类数组转化为数组
(1)arguments
function func() {
console.log([...arguments]);
}
func(1, 2); //(2) [1, 2]
(2)NodeList
console.log([...document.querySelectorAll("p")].push()); //[p, p, p] 3
*/
对象展开运算符的基本用法
/*1.展开对象
//对象不能直接展开,必须在{}中展开
const apple={
color:'红色',
shape:'球形',
taste:'甜'
};
//对象的展开:把属性罗列出来,用逗号分隔,放到一个{}中,构成新对象
//新的对象
// console.log({...apple});//{color: '红色', shape: '球形', taste: '甜'}
*/
/*2.合并对象
const pen = {
color: "黑色",
shape: "圆柱形",
use: "写字",
};
console.log({...pen});
//新对象拥有全部属性,相同属性,后者覆盖前者
console.log({ ...apple, ...pen });//{color: '黑色', shape: '圆柱形', taste: '甜', use: '写字'}
console.log({ pen, apple }); //都有
console.log({ ...pen, apple }); //合并在一起
*/
对象展开运算符的注意事项
//1.空对象的展开
//如果展开一个空对象,则没有任何效果
console.log({ ...{}, a: 1 });//{a: 1}
//2.非对象的展开
//如果展开的不是对象,则会自动将其转为对象,再将其属性罗列出来
console.log({ ...1 }); //{}
console.log(new Object(1)); //Number {1}
console.log({ ...undefined }); //{}
console.log({ ...null }); //{}
console.log({ ...true }); //{}
//如果展开运算符后面是字符串,它会自动转成一个类似数组的对象,因此返回的不是空对象
console.log({ ..."alex" }); //{0: 'a', 1: 'l', 2: 'e', 3: 'x'}
console.log([..."alex"]); //['a', 'l', 'e', 'x']
console.log(..."alex"); //a l e x
console.log({ ...[1, 2, 3] }); //{0: 1, 1: 2, 2: 3}
//3.对象中对象属性 不会展开的
const apple={
feature:{
taste:'甜'
}
};
const pen={
feature:{
color:'黑色',
shape:'圆柱形'
},
use:'写字'
}
console.log({...apple})//feature 不会展开
console.log({...apple,...pen})//后面覆盖前面的
对象展开运算符的应用 [重要]
//1.
const a = { x: 1, y: 2 };
const c = { ...a };
console.log(c, c === a); //{x:1,y:2} false
/*2.这是默认参数的一种形式*/
(1)
const logUser = ({
username = "ZhangSan",
age = 0,
sex = "male",
} = {}) => {
console.log(username, age, sex);
};
(2)
const logUser = (userParam) => {
const defaultParam = {
username: "zhangsan",
age: 0,
sex: "male",
};
const param = { ...defaultParam, ...userParam };
console.log(param.username);
// const {username, age, sex}={...defaultParam,...userParam};
// console.log(username, age, sex)
};
logUser();
Set 和 Map 数据结构
Set 是什么
//1.什么是 Set
//[1,2];
//数组是一系列有序的数据集合
//Set 是一系列无序,没有重复值的数据集合
//2.理解 Set
// console.log([1,2,1]);
// console.log(new Array(1,2,1));//[1, 2, 1]
//Set 中不能有重复的成员
// const s=new Set();
// s.add(1);
// s.add(2);
// console.log(s);//Set(2) {1, 2}
//Set 没有下标去标示每一个值,所以 Set 是无序的,也不能像数组那样通过下标去访问 Set 的成员
Set 实例的方法和属性[重点]
//1.方法
//(1)add
const s=new Set();
s.add(1).add(2).add(2);
// console.log(s);
//(2)has 判断是否有某个成员的
console.log(s.has(1));
console.log(s.has(3));
//(3)delete
//使用 delete 删除不存在的成员,什么都不会发生,也不会报错
s.delete(1);
s.delete(3);
console.log(s);
//(4)clear 一键清除
s.clear();
console.log(s);
//(5)forEach-[重要]遍历 set,给我们提供一个访问 set 成员的一个方式
//forEach 第一个是回调函数,第二个是指定回调函数中 this 指向是什么
s.forEach(function (value,key,set){
//Set 中 value=key
console.log(value,key,set);//2 2 true
console.log(this);//#document
},document);
console.log(s);
//forEach 按照成员添加进集合的顺序遍历
//2.属性
//size
console.log(s.size);//2
console.log(s);//Set(2) {1, 2}
Set 构造函数的参数[重要]
<p>1</p>
<p>2</p>
<p>3</p>
<script>
//1.数组
const s = new Set([1, 2, 1]);
console.log(s);
//2.
// (1)字符串
console.log(new Set("hi"));
// (2)arguments
function func() {
console.log(new Set(arguments));
}
// (3)NodeList
console.log(new Set(document.querySelectorAll("p")));
// (4)Set
const s = new Set([1, 2, 1]);
console.log(new Set(s)===s);//复制
console.log(s);
</script>
Set 的注意事项
//1.判断重复的方式
const s = new Set([1, 2, 1]);
console.log(1 === 1);//true
console.log(NaN===NaN);//false
//Set 对重复的判断基本遵循严格相等(===)
const s=new Set([NaN,2,NaN]);//Set(2) {NaN, 2}
//但是对于 NaN 的判断与 === 不同,Set 中 NaN 等于 NaN
const s=new Set();
s.add({}).add({});
console.log({}==={});//false
console.log(s);//Set(2) {{…}, {…}}
// 2.什么时候使用 Set
// ①数组或字符串去重时
// ②不需要通过下标访问,只需要遍历时
// ③为了使用 Set 提供的方法和属性时(add delete clear has forEach size 等)
Set 的应用[重点]
//1.数组去重
console.log([...new Set([1,2,1])]);
//2.字符串去重
console.log([...new Set('abbacbd')].join(''));
//3.存放 DOM 元素
const s=new Set(document.querySelectorAll('p'))
console.log(s)
s.forEach(function(elem){
elem.style.color='red';
elem.style.backgroundColor='yellow'
})
Map 是什么
//Map 和对象都是键值对的集合
//键->值,key->value
const person={
name:'alex',
age:18
};
const m=new Map();
m.set('name','alex');
m.set('age',18);
console.log(m);//Map(2) {'name' => 'alex', 'age' => 18}
//2.Map 和对象的区别
//对象一般用字符串当做键
const obj = {
name: 'alex',
true: 'true',
[{}]: 'object'
};
console.log(obj);//{name: 'alex', true: 'true', [object Object]: 'object'}
console.log({}.toString());//[object Object]
//基本数据类型:数字,字符串,布尔值,undefined,null
//引用数据类型:对象([],{},函数,Set,Map 等)
//以上都可以作为 Map 的键
const n = new Map();
n.set("name", "alex");
n.set(true, "true");
n.set({}, "object");
n.set(new Set([1, 2]), "set");
n.set(undefined, "undefined");
console.log(n); //Map(5) {'name' => 'alex', true => 'true', {…} => 'object', Set(2) => 'set', undefined => 'undefined'}
Map 实例的属性和方法[重点]
//1.方法
//(1)set : get 获取指定的成员 add:不能单独获取某一个成员,只能通过 forEach 来遍历所有成员
const m=new Map();
//使用 set 添加的新成员,键如果已经存在,后添加的键值对覆盖已有的
m.set('age',18).set(true,'true').set('age',20);
console.log(m);
//(2)get
console.log(m.get('age'));
console.log(m.get('true'));//get 获取不存在的成员,返回 undefined
console.log(m.get(true));
//(3)has:判断有没有指定的数..键
//(4)delete: 删除不存在的成员,什么都不会发生,也不会报错
m.delete('age')
//(5)clear
m.clear()
//(6)forEach
m.forEach(function(value,key,map){
// console.log(value,key,map===m);
console.log(this);
},document)
//2.属性
//size: 获取 map 有几个成员 对象没有类似的属性
console.log(m.size);
Map 构造函数的参数[重点]
//1.数组
//只能传二维数组,而且必须体现出键和值
console.log(
new Map([
["name", "alex"],
["age", 18],
])
);
//2.Set,Map 等
//Set 中也必须体现出键和值
const s = new Set([
["name", "alex"],
["age", 18],
]);
console.log(new Map(s));
console.log(s);
//Map
const m1 = new Map([
["name", "alex"],
["age", 18],
]);
console.log(m1);//Map(2) {'name' => 'alex', 'age' => 18}
const m2=new Map(m1);//Map 复制
console.log(m2,m2===m1);//false
Map 的注意事项
//1.基本遵循严格相等(===)
//例外就是 NaN,Map 中 MaN 也是等于 NaN
console.log(NaN === NaN);//false
const m = new Map();
m.set(NaN, 1).set(NaN, 2);
console.log(m);//Map(1) {NaN => 2}
//2.如果只是需要 key->value 的结构,或者需要字符串以外的值做键,使用 Map 更合适
//forEach 对象 for in
//size
//只有模拟现实世界的实体时,才是用对象
const person={};
Map 的应用[重点]
作业: 也可用 map???映射,map 的 forEach
const [p1, p2, p3] = document.querySelectorAll("p");
// console.log(p1,p2,p3);
/*(1)
const m=new Map();
m.set(p1,'red');
m.set(p2,'green');
m.set(p3,'blue');*/
//(2)
const m = new Map([
//对象字面量形式,,也可用 map???映射,map 的 forEach
[p1, { color: "red" }],
[p2, { color: "green" }],
[p3, { color: "blue", backgroundColor: "orange", fontSize: "40px" }],
]);
// m.forEach((color, elem) => {
// elem.style.color = color;
// }); [p1,'red']
m.forEach((propObj, elem) => {
for (const p in propObj) {
elem.style[p] = propObj[p];
}
});
console.log(m);
遍历器与 for...of 循环
Iterator 是什么
Iterator 的作用
寻找 Iterator
使用 Iterator
什么是 Iterator
//1.Iterator:遍历器(迭代器)
//for() [1,2].forEach()
// new Set().forEach()
//2.console.log([1,2][Symbol.iterator]());
//3.it:可遍历对象(可迭代对象):有 next 方法,而且 next 方法调用之后返回一个对象,这对象会有 value 和 done 两个属性
const it=[1,2][Symbol.iterator]();
console.log(it.next());//{value: 1, done: false}
console.log(it.next());//{value: 2, done: false}
console.log(it.next());//{value: undefined, done: true}
//4.Symbol.iterator (可遍历对象的生成方法) -> it(可遍历对象) ->it.next() ->...(直到 done 为 true)
Iterator 解惑
1.为什么需要 Iterator 遍历器
遍历数组:for 循环和 forEach 方法
遍历对象:for in 循环
Iterator 遍历器是一个统一的遍历方式[数组对象都可以使用其遍历]
// console.log([][Symbol.iterator]());//Array Iterator {}
// console.log({}[Symbol.iterator]);//undefined
2.如何更方便的使用 Iterator
//麻烦:Symbol.iterator->it->next();
我们一般不会直接使用 Iterator 去遍历
//for..of
认识 for.of
//1.
const arr=[1,2,3];
/* const it=arr[Symbol.iterator]();
let next= it.next();
console.log(next);//{value:1,done:false}
while (!next.done){
console.log(next.value);
next=it.next();
console.log(next);
}*/
//(3)隐藏上述步骤,封装[大部分使用这]
for (const item of arr){
console.log(item);//1 2 3
}
//for...of 循环只会遍历出那些 done 为 false 时,对应的 value 值
for...of 的用法[经常使用]
与 break,continue 一起使用
在 for...of 中取得数组的索引
//2.
const arr=[1,2,3];
for(const item of arr){
if(item===2){
// break;跳出循环
continue//只跳过 2,继续循环
}
console.log(item);
}
//3.keys()得到的是索引的可遍历对象,可以遍历出索引值
console.log(arr.keys());
for(const key of arr.keys()){
console.log(key);//0 1 2
}
//4.values() 得到的是值的可遍历对象,可以遍历出值
for(const value of arr.values()){
console.log(value);
}
// 下面简单些
for(const value of arr){
console.log(value);
}
//5.entries() 得到的是索引+值组成的数组的可遍历对象
for(const entries of arr.entries()){
console.log(entries);//[0,1].
}
//解构赋值写法
for(const [index,value] of arr.entries()){
console.log(index,value);
}//0 1 ,1 2
原生可遍历[标红]和非原生可遍历
什么是可遍历
原生可遍历的有哪些?
非原生可遍历的有哪些?
//1.只要有 Symbol.iterator 方法,并且这个方法可以生成可遍历对象,就是可遍历的,就可以使用 for...of 循环来统一遍历
//2.数组,字符串,Set,Map,arguments,NodeList
for (const item of [1, 2, 3]) {
console.log(item); //1 2 3
}
for (const item of "hi") {
console.log(item); //h i
}
for (const item of new Set([1, 2, 3])) {
console.log(item); //1 2 3
}
for (const elem of document.querySelectorAll("p")) {
console.log(elem);
elem.style.color = "red";
}
//3.一般的对象
const person = { sex: "male", age: 18 };
//console.log(person[Symbol.iterator]());×× 用 for in 遍历 person 对象
//for(const item of person){}//person is not iterable
/*下面的一般工作用不到,帮助理解 Symbol.iterator,简单理解下*/
person[Symbol.iterator] = () => {
let index = 0;
return {
next() {
index++;
if (index === 1) {
return {
value: person.age,
done: false,
};
} else if (index === 2) {
return {
value: person.sex,
done: false,
};
} else {
return {
done: true,
};
}
},
};
};
for (const item of person) {
console.log(item);
}
//4.有 lenth 和索引属性的对象
//(1)
const obj = {
'0': 'alex',
'1': 'male',
length: 2
};
obj[Symbol.iterator] =Array.prototype[Symbol.iterator];
/*(2)
const obj = {
0: "alex",
1: "male",
lenth: 2,
};
obj[Symbol.iterator] = () => {
let index = 0;
return {
next() {
let value, done;
if (index < obj.lenth) {
value = obj[index];
done = false;
} else {
value = undefined;
done = true;
}
index++;
return {
value,
done,
};
},
};
};*/
for (const item of obj) {
console.log(item);
}//alex male
使用了 Iterator 的场合[标红]
//原始可遍历的
//Array 数组,String 字符串,Set,Map,函数的 arguments 对象,NodeList 对象
//for..of
//1.数组的展开运算符
console.log(...[1,2,3]);//1 2 3
console.log(...'str');//s t r
console.log(...new Set([1,2,3]));//1 2 3
console.log(...{});×,不能按照数组展开,是不可遍历的
console.log({...{}});//按照对象展开
//2.数组的解构赋值
const [a,b]=[1,2];//1 2
const [a,b]=[...[1,2]];
const [a,b]='hi';
const [a,b]=[...'hi'];//h i
const [a,b]=[...new Set([3,4])];
console.log(a,b);
//3.Set 和 Map 的构造函数
new Set(iterator)
new Map(iterator)
ES6 的新增方法
字符串的 includes()[常用]
//1.判断字符串中是否含有某些字符
//1.基本用法
console.log('abc'.includes('a'));//true
console.log('abc'.includes('ac'));//false
//2.第二个参数
//表示开始搜索的位置,默认是 0
console.log('abc'.includes('a'));
console.log('abc'.includes('a',0));//true
console.log('abc'.includes('a',1));//false
//3.应用[bug:如果本身有?,添加&]
let url='https://www.imooc.com/course/list'
const addURLParam=(url,name,value)=>{
url+=url.includes('?')?'&':'?';
url+=`${name}=${value}`;
return url;
};
url=addURLParam(url,'c','fe');
console.log(url);//https://www.imooc.com/course/list?c=fe
url=addURLParam(url,'sort','pop');
console.log(url);//https://www.imooc.com/course/list?c=fe&sort=pop
padStart()和 padEnd()
//补全字符串长度
//1.基本用法
console.log('x'.padStart(5,'ab'));//ababx
console.log('x'.padEnd(5,'ab'));//xabab
console.log('x'.padEnd(4,'ab'));//xaba
//2.注意事项
//原字符串的长度,等于或大于最大长度,不会消减原字符串,
// 字符串补全不生效,返回原字符串
console.log('xxx'.padStart(2,'ab'));//xxx
console.log('xxx'.padEnd(2,'ab'));//xxx
//用来补全的字符串与原字符串长度之和超过了最大长度,
// 截去超出位数的补全字符串,原字符串不动
console.log('abc'.padStart(10,'0123456789'));//0123456abc
console.log('abc'.padEnd(10,'0123456789'));//abc0123456
//如果省略第二个参数,默认使用空格补全长度
console.log('x'.padStart(4));
console.log('x'.padEnd(4));
//3.应用: 显示日期格式
//2022-10-01
console.log('10'.padStart(2,0));//10
console.log('1'.padStart(2,0));//01
trimStart()和 trimEnd()
//清除字符串的首尾空格,中间的空格不会清除
//1.基本用法
const s = ' a b c ';
console.log(s);
console.log(s.trimStart());//a b c
//console.log(s.trimLeft());//a b c 去头 别名
console.log(s.trimEnd());// a b c
//console.log(s.trimRight());// a b c 去尾
console.log(s.trim());//去首尾空格
//2.应用: 表单提交
const usernameInput=document.getElementById('username');
const btn=document.getElementById('btn');
btn.addEventListener('click',()=>{
console.log(usernameInput.value);
//验证
if(usernameInput.value.trim()!==''){
console.log('可以提交');
}else{
console.log('不能提交');
}
},false)
数组的 includes()[标红]
//判断数组中是否含有某个成员
console.log([1, 2, 3].includes('2'));//false
console.log([1, 2, 3].includes(2));//true
//第二个参数表示搜索的起始位置,默认值是 0
console.log([1, 2, 3].includes(2,2));//false
//基本遵循严格相等(===),但是对于 NaN 的判断与===不同,,includes 认为 NaN===NaN
console.log(NaN===NaN);//false
console.log([1,2,NaN].includes(NaN));//true
//2.应用: 去重
const arr=[];
for (const item of[1,2,1]){
if (!arr.includes(item)){
arr.push(item);
}
}
console.log(arr);//(2) [1, 2]
Array.from()[标红]
//将其他数据类型转换为数组
//1.基本用法
console.log(Array.from('str'));//['s', 't', 'r']
//2.哪些可以通过 Array.from()转换成数组?
//2.1 所有可遍历的
//数组,字符串,Set,Map,NodeList,arguments
console.log(Array.from(new Set([1,2,1])));//(2) [1, 2]
console.log([...new Set([1,2,1])]);//推荐 (2) [1, 2]
//2.2 拥有 length 属性的任意对象
const obj={
'0':'a',
'1':'b',
name:'aled',
length:3
};
//console.log([...obj]);//错误的
console.log(Array.from(obj));//(3) ['a', 'b', undefined]
//3.第二个参数
//作用类似于数组的 map 方法,用来对每个元素进行处理,将处理后的值放入返回的数组
console.log(
[1, 2].map(value => {
return value * 2;
}))//(2) [2, 4]
// console.log(Array.from('12',value=>value*2));//(2) [2, 4]
// console.log(Array.from('12').map(value=>value*2));//(2) [2, 4]
//4.第三个参数
Array.from('12',value=>{
console.log(this);
},document);//this 指向 window
Array.from('12',function (){//一般函数可以修改 this 指向
console.log(this);
},document);
find()和 findIndex()[了解]
//find():找到满足条件的一个立即返回
//findIndex():找到满足条件的一个,立即返回其索引
//1.基本用法
[1, 5, 10, 15].find((value, index, arr) => {
// console.log(value, index, arr);
console.log(this);//指向 window,若要改变指向,则换为一般函数
return value > 9;
});
console.log(
[1, 5, 10, 15].findIndex((value, index, arr) => {
// console.log(value,index,arr);
return value > 9;
}) );//2
//2.应用
const students = [
{
name: '张三',
sex: '男',
age: 16
},
{
name: '李四',
sex: '女',
age: 13
}
];
console.log(students.find(value=>value.sex==='女'));//第一个女学生
console.log(students.findIndex(value=>value.sex==='女'));//1
Object.assign()[标红]
//用来合并对象
//1.基本用法
// Object.assign(目标对象,源对象 1,...);返回目标对象
const apple = {
color: '红色',
shape: '圆形',
taste: '甜'
};
const pen = {
color: '黑色',
shape: '圆柱形',
use: '写字'
};
console.log(Object.assign(apple, pen));//相同属性,后面覆盖前面的
//Object.assign 直接合并到了第一个参数中,返回的就是合并后的对象===apple
//返回一个新对象: 可以合并多个对象
console.log(Object.assign({},apple, pen));//apple 不会发生变化
console.log({...apple, ...pen});//是个新对象
//2.注意事项
//2.1 基本数据类型作为源对象
//与对象的展开类似,先转换成对象,再合并
console.log(Object.assign({},undefined));//{}
console.log(Object.assign({},null));//{}
console.log(Object.assign({},1));//{}
console.log(Object.assign({},true));//{}
console.log(Object.assign({},'str'));//{0: 's', 1: 't', 2: 'r'}
//2.2 同名属性的替换: 后面的直接覆盖前面的 color:['黑色','银色']一起覆盖前面的
console.log(Object.assign({},apple,pen));
//3.应用:合并默认参数和用户参数
const logUser=userOptions=>{
const DEFAULTS={
username:'Zhangsan',
age:0,
sex:'male'
};
const options=Object.assign({},DEFAULTS,userOptions);
console.log(options);
};
// const options=Object.assign({},DEFAULTS,undefined);
logUser();//相当于传一个 undefined
logUser({});//默认参数
logUser({username:'Alex'});//{username: 'Alex', age: 0, sex: 'male'}
Object.keys()、Object.values()和 Object.entries()
//1.基本用法
const person={
name:'Alex',
age:18
};
console.log(Object.keys(person));//['name', 'age']
console.log(Object.values(person));//['Alex', 18]
console.log(Object.entries(person));//二维数组 [Array(2), Array(2)]
//2.与数组类似方法的区别
/*对象的 Object.keys...是构造函数方法,返回的是数组
数组的 keys...等方法是实例方法,返回的是数组的遍历对象 Iterator*/
console.log([1,2].keys());
console.log([1,2].values());
console.log([1,2].entries());
//3.使用 for..of 循环遍历对象
for(const key of Object.keys(person)){
console.log(key);//name age
}
for(const value of Object.values(person)){
console.log(value);
}
for(const entries of Object.entries(person)){
console.log(entries);//(2) ['name', 'Alex'] ['age', 18]
}
for (const [key, value] of Object.entries(person)) {
console.log(key, value); //(2) name Alex age 18
}
//Object.keys()/values()/entries() 并不能保证顺序一定是你看到的样子,这一点和 for in 是一样的
总结