ES6
ECMA6Script
ECMAScript 6,简称ES6,是JavaScript语言的一次重大更新
由于VUE3中大量使用了ES6的语法,所以ES6成为了学习VUE3的门槛之一
- 更加简洁:
- 更强大的功能
- 更好的实用性
ES6的变量和模板字符串
ES6中新增了let和const,用来声明变量,使用的细节存在差异
let和var的区别
- let不能重复声明
var i = 10
var i ="hello"
let j = 10
let j = "hello"//报错,let不能重复声明 Uncaught SyntaxError: Identifier 'j' has already been
- let有块级作用域,非函数的花括号遇见let也会有块级作用域
{
var i = 10
let j = 10
}
console.log(i) //10
console.log(j) //变量j未被定义 Uncaught ReferenceError: j is not defined
- let不会预解析进行变量提升
console.log(a) //undefined
var a =10
console.log(j) //变量j未被预解析 Uncaught ReferenceError: Cannot access 'j' before initialization
let j =10
- let定义的全局变量不会作为windows(Bom编程)的属性
var a = 10 //a会变成window的属性
console.log(window.a) //10
let b =10
console.log(window.b) //undefined
- let在es6中推荐优先使用
const
const中文释义:常数;恒量
const就是不可修改的let
类似于java中被final修饰的数(常量)
- const的值不可被修改
const a = 10
a = 20 // Uncaught TypeError: Assignment to constant variable.
- const的值不可为空
const a //Uncaught SyntaxError: Missing initializer in const declaration
- const可以设置常量值
const PI = 3.14;
- const内容为对象时,不可以修改其值的本质是不可修改引用,其内容还是可以发生变化的
const techers = ["张老师", "王老师", "李老师"];
//techers = ["","",""] //无法修改 Uncaught TypeError: Assignment to constant variable.
techers.push("赵老师");
console.log(techers); //['张老师', '王老师', '李老师', '赵老师']
模板字符串
模板字符串用以处理字符串换行和字符串拼接问题
" "或者' '中的传统字符串是不支持多行
``中的字符支持多行且拼接变量可以直接用${}的方式
` 反单引号(backquote),又称反引号,是西文字符中的附加符号,主要用于计算机领域
<script>
let city = "长春";
let str =
`<ul>
<li>${city}</li>
<li></li>
<li></li>
<li></li>
<li></li>
</ul>`;
console.log(str);
</script>
${变量}在字符串中的使用是获取变量内容并进行字符串拼接
${表达式}在JSP中是EL表达式,作用是获取表达式的值
ES6的解构表达式
解构数组和对象
<script>
let arr = [11,22,33,44]
//解构表达式取出数组中的元素
let [a,b,c,d,e = 10] = arr
console.log(a,b,c,d,e) //11 22 33 44 10
let person = {
name : "xiaobai",
age : 18
}
//使用解构表达式获取对象的属性值
let {name,age} = person
console.log(name,age)
</script>
当使用解构表达式解构对象时,其属性值的获取是根据属性名获取的(不同于数组的索引)
所以无法给非属性名的变量赋值解构
let person = {
name : "xiaobai",
age : 18
}
//使用解构表达式获取对象的属性值
let {x,y} = person
console.log(x,y) //undefined undefined
解构表达式作为方法的形参
<script>
let arr = [11,22,33,44]
//解构表达式作为形参使用
function showArr([a,b,c=10]){
console.log(a,b,c)
}
showArr(arr)
</script>
ES6的箭头函数
ES6允许使用"箭头"函数,语法类似Java中的Lambda表达式
在java中,lambda表达式多用于结合函数式接口实现匿名内部类的功能,而js中多用于定义函数(方法)
其中括号内是形参,大括号是执行体,而js是弱类型无需函数返回类型和形参类型,函数名即为赋值给的变量名
<script>
let fun1 = function(){} //普通的函数声明
let fun2 = () => {} //箭头表达式(lambda)
let fun3 = (x) => { return x+1 }
let fun4 = x => { return x+1 } //当参数只有一个的时候 小括号省略
let fun5 = x => console.log(x) //当执行语句只有一条的时候 大括号省略
let fun6 = x => x+1 //当执行语句只有一条且时return时 大括号和return都省略
</script>
箭头函数中的this问题
箭头函数中,没有自己的this
箭头函数中的this时外层上下文环境的this
let person ={
name : "xiaobai",
showName:function(){
console.log(this.name)
},
viewName:() => {
console.log(this.name)
},
viewThis:() =>{
console.log(this)
}
}
person.showName() //xiaobai
person.viewName() //空白
person.viewThis() //Window对象
每当使用箭头函数时,其this为上一层对象,如果实在找不到this就直接打印出来
rest和spread
rest剩余参数
rest中文释义:剩余的
rest在js的用法相当于java的可变参数,其在形参中的最后使用且只能有一个,写法是... arr
无论参数的类型是什么,有多少,都以数组的形式接受剩余参数
let fun1 = (... arr) => { console.log(arr) }
fun1(1,2,3,4,5,6,7,8,9,"str")
spread实参传递
spread中文释义:扩散;展开
和rest的写法相同,在调用方法时作为实参使用
在传入实参时将数组内容扩散展开分别为形参赋值
let arr = [1,2,3]
let fun = (a,b,c) => {
console.log(a,b,c)
}
fun(arr) //[1, 2, 3] undefined undefined
fun(...arr) //1 2 3
在形参中使用解构表达式,直接将数组作为实参也能完成此功能
spread合并数组
spread可以快速合并数组
let a = [1,2,3]
let b = [4,5,6]
let c = [7,8,9]
let d = [...a,...b,...c]
console.log(d) //[1, 2, 3, 4, 5, 6, 7, 8, 9]
spread合并对象
spread可以快速合并对象
注:如果有重名对象,后者会覆盖前者
let person1 = {name:"张三",age:"10"}
let person2 = {name:"小白",age:"18",gender:"boy"}
let person3 = {salary:"3000"}
let person4 = {...person1,...person2,...person3}
console.log(person4)//{name: '小白', age: '18', gender: 'boy', salary: '3000'}
对象创建的语法糖
ES6中新增了对象创建的语法糖,支持了class extends constructor等关键字,让ES6的语法和面向对象的语法更加接近
class Person{
//属性
name;
#age;
//getter/setter
get name(){
return this.name
}
set name(name){
this.name = name
}
get setage(){
return this.#age
}
set setage(age){
this.#age = age
}
//实例方法
eat(food){
console.log(`${this.age}岁的${this.name}正在吃${food}`)
}
//静态方法
static sum(a,b){
return a+b
}
//构造方法
constructor(name,age){
this.name = name
this.#age = age
}
}
js中没有private关键字,要在私有属性前加#,但要注意的是,所有对此属性的操作时,属性名都有#
类的方法
在调用get/set方法时和调用普通的实例方法不同,相当于直接.属性赋值的形式调用
let person = new Person()
person.name = "xiaobai"
person.setage = 18 //调用set方法
console.log(person) //Person {name: 'xiaobai', age: 18}
//私有属性无法通过.属性名的方式访问
console.log(person.#age)//Uncaught SyntaxError: Private field '#age' must be declared in an enclosing class
//调用实例方法
person.eat("火锅") //18岁的xiaobai正在吃火锅
//调用静态方法
console.log(Person.sum(10,20)) //30
//调用构造方法
let person1 = new Person("xiaoming",20)
console.log(person1)
类的继承
在ES6的语法糖中,继承也是可以使用的
class Student extends Person{
score
study(){
console.log(`${this.getage}岁的${this.name}正在努力学习,考试获得了${this.score}分`)
}
constructor(name,age,score){
super(name,age)
this.score = score
}
}
let stu = new Student("xiaobai",18,100)
stu.study() //18岁的xiaobai正在努力学习,考试获得了100分
对象拷贝的语法糖
浅拷贝
浅拷贝是多一个引用指向同一个对象
let arr = [1,2,3]
let arr2 = arr
arr[0] = 100
console.log(arr2) // [100, 2, 3]
person = {name : "xiaobai",age : 18}
person2 = person
person.name = "xiaohei"
console.log(person2) //{name: 'xiaohei', age: 18}
深拷贝
深拷贝是完全一个全新的对象
可以通过spread展开赋值
let arr = [1,2,3]
let arr2 = [...arr]
arr[0] = 100
console.log(arr2) // [1, 2, 3]
person = {name : "xiaobai",age : 18}
person2 = {...person}
person.name = "xiaohei"
console.log(person2) //{name: 'xiaobai', age: 18}
还可以通过json字符串的转换来给对象重新赋值
先将对象转为JSON串,再转换回变量
person = {name : "xiaobai",age : 18}
person2 = JSON.parse(JSON.stringify(person))
person.name = "xiaohei"
console.log(person2) //{name: 'xiaobai', age: 18}