ES6基础
2020-04-29 15:54:45 11 举报
AI智能生成
个人前端学习
作者其他创作
大纲/内容
let
变量声明
1.使用var或者直接使用的变量名定义声明的变量(污染全局对象)
变量声明后,即挂在了全局对象window上,作为其属性和方法,通常也可以省略window对象直接调用;当我们访问不存在的变量时,即会自动创建一个变量,详见本章笔记附录:
变量声明后,即挂在了全局对象window上,作为其属性和方法,通常也可以省略window对象直接调用;当我们访问不存在的变量时,即会自动创建一个变量,详见本章笔记附录:
2、var与let的主要区别:
— —let声明变量 只在当前块级作用域有效(即{}),不会污染全局对象window;
— —let或者const声明变量,不能被重复声明;
— —let不存在变量提升(使用变量前,必须先声明;如果是使用var,会有一个预解析的状态,使变量被赋值为undefined,且使所有的var 和function声明的变量和函数提至最前面)
变量提升:在变量声明前,调用变量,会将变量提升到调用语句前,仍会读到该变量。
— —let声明变量 只在当前块级作用域有效(即{}),不会污染全局对象window;
— —let或者const声明变量,不能被重复声明;
— —let不存在变量提升(使用变量前,必须先声明;如果是使用var,会有一个预解析的状态,使变量被赋值为undefined,且使所有的var 和function声明的变量和函数提至最前面)
变量提升:在变量声明前,调用变量,会将变量提升到调用语句前,仍会读到该变量。
const
声明常量
const 声明常量
1.常量必须在声明的时候赋值,否则报错
2.常量不能被修改, 但是!!为引用类型的时候,可被修改,const只能保证指向的引用地址不变,但是地址中的内容是可以改变的,比如xiaoming.age = 22
1.常量必须在声明的时候赋值,否则报错
2.常量不能被修改, 但是!!为引用类型的时候,可被修改,const只能保证指向的引用地址不变,但是地址中的内容是可以改变的,比如xiaoming.age = 22
与let类似的特性:
不能重复声明;
不存在提升;
只在当前(快级)作用域内有效
常量为引用类型的时候不能保证不可变
不能重复声明;
不存在提升;
只在当前(快级)作用域内有效
常量为引用类型的时候不能保证不可变
const 声明常量时,只能保证常量所指向的地址不变(eg:18、23同地址,25与18、23不同地址),但不能保证地址上的值(23改变的只是18内的值)不去发生改变。类似的还有数组,改变其中的值谋问忒,但改变地址(eg:被赋予新数组)就有问题。
常量内引用Object.freeze()可保证引用类型不被修改;
const扩展
1.Object.defineProperty(对象名,属性名,{value:属性值 }):可添加、修改属性值,也可扩展属性;
对象名:必须,被添加或者修改属性的对象。
属性名:必须,被修改的属性名称
{value:属性值 }:必须,属性描述符,它可以针对数据属性或访问器属性
返回值:已修改的对象。
用法:向对象添加新属性。修改现有的属性特征
对象名:必须,被添加或者修改属性的对象。
属性名:必须,被修改的属性名称
{value:属性值 }:必须,属性描述符,它可以针对数据属性或访问器属性
返回值:已修改的对象。
用法:向对象添加新属性。修改现有的属性特征
通过wirteable:false则可以只读不能修改;
通过wirteable:true之才可以修改新属性值。
例:Object.defineProperty(obj,i,{
writable:false---
});
通过wirteable:true之才可以修改新属性值。
例:Object.defineProperty(obj,i,{
writable:false---
});
2.Object.seal(对象名):让一个对象密封,密封对象不能添加新的属性,不能删除已有的属性,以及不能修改已有属性的可枚举性、可配置性,可写性,但是可以修改已有属性对象的值。
返回值:被密封后的对线
返回值:被密封后的对线
3.Object.hasOwnProperty(属性名):检测是否是自己定义的属性,
属性名:必须
返回值:是则返回true,不是则返回false
属性名:必须
返回值:是则返回true,不是则返回false
ES6扩展
自执行函数原理阐释
(一)基本语法格式
( function (formal arguments){ } ) (actual arguments)
( function (formal arguments){ } ) (actual arguments)
(二)为什么会是这么写的?
1.顾名思义:自执行函数,也就是会随着脚本的加载,会自动执行的函数。
2.函数的使用:我们知道函数要执行,就必须要进行调用,函数的调用方式分为两种,一种是使用functionName(),加以调用;另一种是使用functionVariateName(),即变量名()加以调用。
3.万不离其宗:函数的自执行,也必须按照基本语法来才能调用。
4.对比分析:将自执行函数的基本写法与函数的调用语法对比一下
— —常规调用 :functionName() || functionVariateName()
— —自执行函数:(function(){})()
5.明显的结论:形式上的等价于
(function(){})==functionName==functionVariateName
6.实际的使用形式:
— —(function(formal arguments){})(actual arguments)
— —(functionName)(arguments)
— —(functionVariateName)(arguments)
1.顾名思义:自执行函数,也就是会随着脚本的加载,会自动执行的函数。
2.函数的使用:我们知道函数要执行,就必须要进行调用,函数的调用方式分为两种,一种是使用functionName(),加以调用;另一种是使用functionVariateName(),即变量名()加以调用。
3.万不离其宗:函数的自执行,也必须按照基本语法来才能调用。
4.对比分析:将自执行函数的基本写法与函数的调用语法对比一下
— —常规调用 :functionName() || functionVariateName()
— —自执行函数:(function(){})()
5.明显的结论:形式上的等价于
(function(){})==functionName==functionVariateName
6.实际的使用形式:
— —(function(formal arguments){})(actual arguments)
— —(functionName)(arguments)
— —(functionVariateName)(arguments)
三)我们为什么需要使用自执行函数?
充分发挥自执行函数提供的密闭空间作用域的优势
— —避免污染变量内存,即全局变量window(浏览器端);
— —构建密闭作用域(如老师的代码)
充分发挥自执行函数提供的密闭空间作用域的优势
— —避免污染变量内存,即全局变量window(浏览器端);
— —构建密闭作用域(如老师的代码)
作用域
//ES6之前版本
1.全局作用域(window);
2.函数作用域
3.eval作用域(即是指:eval函数的() 包含的部分)
1.全局作用域(window);
2.函数作用域
3.eval作用域(即是指:eval函数的() 包含的部分)
//ES6
4.块级作用域(即使用 {...} 包含的代码区域)
— —if(){...};
— —switch(){...};
— —for(){...};
包含了两级作用域,()内是一个作用域,{}是其子作用域
— —try(){...}catch(err){...};
— —{...}
tips:支持嵌套块级作用域;除对象的{}外;
5.暂存死区:
只要在块级作用域中,使用let或const关键字声明变量之前,该变量都是不可用的。这在语法上,称为“暂时性死区”
4.块级作用域(即使用 {...} 包含的代码区域)
— —if(){...};
— —switch(){...};
— —for(){...};
包含了两级作用域,()内是一个作用域,{}是其子作用域
— —try(){...}catch(err){...};
— —{...}
tips:支持嵌套块级作用域;除对象的{}外;
5.暂存死区:
只要在块级作用域中,使用let或const关键字声明变量之前,该变量都是不可用的。这在语法上,称为“暂时性死区”
解构赋值
数组的结构赋值
一、简单的解构赋值:
const arr = [1,2,3,4];
let [a,b,c,d]= arr;
我的理解就是,数组的解构赋值是提供已知数据的数组a,赋值给相同结构、内容为变量的数组b,这样一次性的把b都给赋值了。
const arr = [1,2,3,4];
let [a,b,c,d]= arr;
我的理解就是,数组的解构赋值是提供已知数据的数组a,赋值给相同结构、内容为变量的数组b,这样一次性的把b都给赋值了。
二、更复杂的匹配规则:
const arr = ['a','b',['c','d',['e','f','g']]];
const [ , ,[ , ,[ , ,g]]]=arr;
这样的话,就是变量g只取数组arr中的'g',但是变量g所在的数组的结构要和数组arr匹配,逗号不能少;
const arr = ['a','b',['c','d',['e','f','g']]];
const [ , ,[ , ,[ , ,g]]]=arr;
这样的话,就是变量g只取数组arr中的'g',但是变量g所在的数组的结构要和数组arr匹配,逗号不能少;
三、扩展运算符:
const arr1 = [1,2,3];
const arr2 = ['a','b'];
const arr3 = ['zz',1];
const arr4 = [...arr1, ...arr2, ...arr3];
如果arr4中不加... ,那么数组arr4中显示的就是[Arr1,Arr2,Arr3],如果加上... ,那么arr4中显示的就是一个数组,这个数组是前三个数组的集合[1, 2, 3, "a", "b", "zz", 1]。
const arr1 = [1,2,3];
const arr2 = ['a','b'];
const arr3 = ['zz',1];
const arr4 = [...arr1, ...arr2, ...arr3];
如果arr4中不加... ,那么数组arr4中显示的就是[Arr1,Arr2,Arr3],如果加上... ,那么arr4中显示的就是一个数组,这个数组是前三个数组的集合[1, 2, 3, "a", "b", "zz", 1]。
结合扩展运算符和结构赋值
const arr = [1,2,3,4,5,6];
const [a,b,...c] = arr;
这样,c的结果就是[3, 4, 5, 6],c就是取除了a,b后面所有的值;但是扩展运算符和数组的结构赋值结合的话,数组变量中,扩展运算符只可以放在最后,后面 不可以有变量([a,b,...c,d]这样就是错的)。
const arr = [1,2,3,4,5,6];
const [a,b,...c] = arr;
这样,c的结果就是[3, 4, 5, 6],c就是取除了a,b后面所有的值;但是扩展运算符和数组的结构赋值结合的话,数组变量中,扩展运算符只可以放在最后,后面 不可以有变量([a,b,...c,d]这样就是错的)。
四、默认值
数组的解构赋值,变量的默认值是undefined
const arr = [1,undefined,undefined];
const [a,b,c,d] = arr;
b、c被赋值给了undefined,d的话,在arr中没有被匹配到,取的是默认值,是undefined;因为const常量被声明的时候必须被赋值,这样写没有报错,说明直接给了默认值;
数组的解构赋值,变量的默认值是undefined
const arr = [1,undefined,undefined];
const [a,b,c,d] = arr;
b、c被赋值给了undefined,d的话,在arr中没有被匹配到,取的是默认值,是undefined;因为const常量被声明的时候必须被赋值,这样写没有报错,说明直接给了默认值;
如果匹配的的数组值是undefined,被匹配的数组,常量中若有给值的话,那么就取用给的值,b为2,c为undefined,d为aaa,也即只有数组是undefined的时候,才可以匹配被给的数值;
但如果arr中给的是null,那么即使被匹配常量中有值的话,也不会取值
(比如const arr=[1,null,undefined] ;
const [a,b=2,c,d='aaa'] = arr;这样b还是不等于2,b被取值为null)。
但如果arr中给的是null,那么即使被匹配常量中有值的话,也不会取值
(比如const arr=[1,null,undefined] ;
const [a,b=2,c,d='aaa'] = arr;这样b还是不等于2,b被取值为null)。
五、交换变量
ES6之前,交换变量的方法是给创建一个新的变量,然后进行交换;
利用解构赋值交换会很方便:
let a = 20;
let b = 10;
[a,b] = [b,a];
ES6之前,交换变量的方法是给创建一个新的变量,然后进行交换;
利用解构赋值交换会很方便:
let a = 20;
let b = 10;
[a,b] = [b,a];
六、接收多个 函数返回值
function getUserInfo(id){
return [
true,
{
name:'小明',
gender:'女',
id:'id'
},
'请求成功'
];
};
const [status,data,msg] = getUserInfo(123);
因为这样函数执行后返回的是一个数组(数组中是一个布尔值,一个对象,一个字符串),这样就可以用到解构赋值了,赋值给三个常量;
之前的做法是将函数的执行赋值给一个变量a(或者常量),然后通过变量a[i]赋值给各个变量b(或常量),打印变量b的时候就可以看到各个函数的返回值。
function getUserInfo(id){
return [
true,
{
name:'小明',
gender:'女',
id:'id'
},
'请求成功'
];
};
const [status,data,msg] = getUserInfo(123);
因为这样函数执行后返回的是一个数组(数组中是一个布尔值,一个对象,一个字符串),这样就可以用到解构赋值了,赋值给三个常量;
之前的做法是将函数的执行赋值给一个变量a(或者常量),然后通过变量a[i]赋值给各个变量b(或常量),打印变量b的时候就可以看到各个函数的返回值。
对象的解构赋值
1.数组与对象区别
数组有序,根据下标取值;
对象是无序的,结构赋值时,变量名和对象的属性名相同,就可以匹配,取到对象中属性的属性值;
数组有序,根据下标取值;
对象是无序的,结构赋值时,变量名和对象的属性名相同,就可以匹配,取到对象中属性的属性值;
2.无需保留前项位置,即使用逗号;
3.赋值对象匹配---如图
当对象为中其中一个属性为数组时,则需按照数组方式来解析结构,另当前者为数组的同时,里面的数组项为对象时,获取相同的属性名,则不能写相同的属性名(const 申明的变量名不能重名)---------用:隔开,只可前者属性名相同,同时将属性值赋予;后者则是需要属性名:属性值(变量名称),是将其属性名的属性值赋予变量
*****对象的解构赋值的内部机制,是先找到同名属性,然后再赋给对应的变量,
当对象为中其中一个属性为数组时,则需按照数组方式来解析结构,另当前者为数组的同时,里面的数组项为对象时,获取相同的属性名,则不能写相同的属性名(const 申明的变量名不能重名)---------用:隔开,只可前者属性名相同,同时将属性值赋予;后者则是需要属性名:属性值(变量名称),是将其属性名的属性值赋予变量
*****对象的解构赋值的内部机制,是先找到同名属性,然后再赋给对应的变量,
要拿某个属性只要构造相同的数据结构就行,属性重名时可以在属性后加个:,形成A:B,表示拿A的属性但是复制给B
4.扩展运算符...
1)可通过扩展运算符,匹配后面所有的属性
const obj = {
saber:'阿尔托利亚',
archer:'卫宫',
lancer:'瑟坦达'
};
const{saber,...oth }= obj;----表示将将剩下的两项以oth为名的对象;
同样扩展运算符不能在中间,只能在末尾
1)可通过扩展运算符,匹配后面所有的属性
const obj = {
saber:'阿尔托利亚',
archer:'卫宫',
lancer:'瑟坦达'
};
const{saber,...oth }= obj;----表示将将剩下的两项以oth为名的对象;
同样扩展运算符不能在中间,只能在末尾
2)...扩展运算符也可使用,独享合并
const obj1 = {
archer:'卫宫',
lancer:'瑟坦达'
}
const obj = {
saber:'阿尔托利亚',
...obj1
};-----将obj1的属性合病到obj
const obj1 = {
archer:'卫宫',
lancer:'瑟坦达'
}
const obj = {
saber:'阿尔托利亚',
...obj1
};-----将obj1的属性合病到obj
5.默认值
与数组相似,当匹配到undefind,就会取默认值;
let girlfriend = {
name:'小红',
age:undefind,
};
let {name ,age = 24, hobby = ['学习'] } = girlfriend;----age则为默认值24岁,当不是时,则匹配到属性值;
与数组相似,当匹配到undefind,就会取默认值;
let girlfriend = {
name:'小红',
age:undefind,
};
let {name ,age = 24, hobby = ['学习'] } = girlfriend;----age则为默认值24岁,当不是时,则匹配到属性值;
字符串的解构赋值
1.通过数组形式来匹配字符串;
2.扩展运算符...
...oth 是将剩下的字符串的字母以数组的形式全部拆分为25个字母,而非单词;
...oth 是将剩下的字符串的字母以数组的形式全部拆分为25个字母,而非单词;
3.图中的三种方式都是如第2点所诉,以数组的形式全部拆分为单独字母,而非单词;
1.关于oth,把剩下的以数组的形式赋值给oth
2.切割字符串的三种方式
const [...spStr1] = str;
const spStr2 = str.spilt('');
const spStr3 = [...str];
3.提取属性
const {length}=str
2.切割字符串的三种方式
const [...spStr1] = str;
const spStr2 = str.spilt('');
const spStr3 = [...str];
3.提取属性
const {length}=str
数值与布尔值的解构赋值
1.当str(字符串).length时,是将字符串临时包装成对象获取,获取完后,又重新返回str;
函数参数的解构赋值
0 条评论
下一页