1.ES6中的let关键字和val关键字声明变量的区别
var关键字是原生JS中声明变量的关键字,let关键字是ES6语法中新增关键字
let关键字声明的变量不能重复声明,var关键字可以重复声明变量
let关键字解析变量没有预解析,var关键字声明的变量包含预解析过程
let关键字提供了块级作用域,var关键字没有块级作用域,只有局部、全局作用域
2.简述模板字符串的使用优势
常规字符串中如果需要进行字符串和变量数据的拼接,需要通过连接符号+进行拼接,如果字符串和拼接 变量数量较多,拼接过程非常繁琐,代码阅读非常不便利
模板字符串是ES6新增的语法,使用反引号包含一串字符,变量可以通过固定语法${}的形式在字符串内部直接使用和操作,相当于提升了操作效率
3.ES6语法中对数组进行了哪些改进
ES6语法中针对数组的创建和其他类数组提供了两个常用的函数
Array.of() 用于新建数组对象
Array.from() 用于将其他类数组转换成数组
4.简述ES6中数组解构赋值都有哪几种操作方式
解构赋值的操作,数组的解构主要包含如下几种
-完全解构
-不完全解构
-解构失败| 过度解构
-解构默认值
-缺省解构
5.简述你对ES6中对象解构赋值的认识
ES6中提供的对象解构语法包含如下几种
-完全解构
-简洁语法解构
-不完全解构,是代码中使用最频繁的操作
6.let {toString:f} =100,请描述f的值是什么,为什么
f打印出来是一个函数
100是一个数值类型,本质上是一个Number对象,对象包含toString()函数用于输出数据,解构赋值中将Number对象中的toString进行了解构,所以解构中赋值变量f中存储的就是一个toString函数声明
7.将数组[100,200,[101,201],[301,302]]的值,赋值给变量
let arr = [100,200,[101,201],[301,302]]
let [a,b,[c,d],[e,f]] = arr
8.观察代码说明输出结果
let obj = {a:1,b:2,c:{d:{e:5}}}
let {a,b,c:{d}} = obj
console.log(d) // {e:5} 这里是按照数据的解构进行取值,展示d变量中的数据
//解构默认值
let {a=10,b=5} = {a:3}
console.log(a,b) // 3 5 解构默认值,如果解构得到数据就直接使用,没有数据使用默认值数据
let {a:aa = 10,b:bb = 5} = {a:3}
console.log(aa,bb) // aa=3 bb=5 解构默认值操作原理
let obj = {p:[{y:'world'}]}
let {p:[y],x} = obj
console.log(x,y) //undefined world
9.观察代码,说明输出结果
const userStr = 'zhangsan,lisi,wangwu,zhaoliu'
const {1:a,3:b} = userStr.split(',')
console.log(a,b) // lisi zhaoliu
上述代码中,通过split()函数将字符串拆分成了数组
然后通过解构赋值的方式进行了数据的提取,通过对象解构提取数组中的数据
上述代码中如果不会出现错误的情况下,可以按照索引进行解构
a中解构的数据llisi b中解构的数据zhaoliu
10.关于剩余参数的使用,正确的是 (AB)
A function fn(name,...args) {...}
B function fn(...args) {...}
C function fn(...args,name) {...}
D function fn(...name,...args) {...}
11.声明类型的语法,正确的是(BC)
A class Person() {}
B class Person {}
C function Person() {}
D function Person{}
12.关于ES6中constructor() 的描述,正确的是?(ABD)
A 类型中的构造函数,用来在创建对象的同时初始化对象属性
B 创建指定类型的对象时,会自动调用执行
C 类型中的构造函数,需要手工调用执行
D 类型中的普通函数,需要手工调用执行
13.箭头函数的使用,操作语法正确的是 (BD)
A let fn() = () -> console.log('hello')
B let fn() = () => console.log('hello')
C let fn() = name -> console.log('hello')
D let fn() = () => console.log('hello')
14.箭头函数中的参数的使用,正确的是(BD)
A let fn = name,age => console.log(name,log)
B let fn = (name,age) => console.log(name,log)
C let fn = name,age => {console.log(name,log)}
D let fn = (name,age) => {console.log(name,log)}
15.箭头函数中返回值的操作,正确的是(AD)
A let fn = (x,y) => {x++;y++;return x+y;}
B let fn = (x,y) => {x++;y++; x+y;}
C let fn = (x,y) => return x+y
D let fn = (x,y) => x+y
16.关于类和对象的描述,正确的是(ABD)
A 类表示类型的意思
B 对象是包含数据的、实际存在的物体
C 一个类型只能创建一个对象
D 多个对象可以属于一个类型
17.ES6类型中,对于静态属性和静态函数的操作正确的是 (BC)
A 静态属性是声明在类型内部,类型方法外部的,使用let声明的变量
B 静态属性是声明在类型内部,类型方法外部的,使用static声明的变量
C 静态属性是属于类型的属性,所以只能被类型名称调用
D 静态属性是属于类型的属性,所以可以被类型名称和该类型创建的所有对象调用
18.关于函数中使用默认值,操作方式正确的是(ACD)
A function fn(name) {name = name || 'default',...}
B function fn(name) {name = "default";...}
C function fn(name="default") {...}
D let funtion = (name = 'default') => {...}
19.面向对象的继承关系中,正确的操作语法是(A)
A class Student extends Person {...}
B class Student(Person) {...}
C class Student extends Person() {...}
D class Student extends Person,Job{...}
注:JS中的继承是单继承机制,不能同时继承多个类型
20.观察下面的代码,最终控制台会输出什么结果?请说明原因
let name = 'zhangsan'
function fn() {
console.log(name)
let name = 'lisi'
}
fn()
输出错误,let声明的变量存在暂时性死区,变量声明之前不能使用该变量
21.梳理下面的代码,最终输出的数据是什么?请说明原因
let person = {
'pName': 'zhangsan',
'pAge': 20,
'pSex': 'nale'
}
let {
pName: name,
pAge
} = person
console.log(name);
console.log(pName);
console.log(pAge);
第一个输出zhangsan 别名输出,给pName的值赋值到一个名称为name变量中
第二个错误,一旦出现了别名赋值,原来的属性名称就不能使用
第三个 20
解构赋值中,如果给一个属性添加了别名,属性名称就不能再使用了,所以pName报错
22.解析下面的代码,最终输出什么结果?为什么
for(var i=0;i<10;i++) {
setTimeout(function(){
console.log(i);
})
}
for(let j=0;j<10;j++) {
setTimeout(function(){
console.log(j);
})
}
1.10 ....10 var 声明的变量的作用域只有全局和局部,for循环中多次循环使用的是同一个作用域空间,setTimout()延时函数会在循环全部执行完成后输出,循环中最后一次判断时i=10<10跳出循环,此时最终i的值是10
2.0,1,2,...9 let声明的变量存在块级作用域,for循环每次循环都是一个独立的作用域,延时函数执行的时候相当于在10个不同的作用域中执行,最终输出了差异化的数据
23.过年了,小明一家均长了一岁,重新记录到一个新的变量中,请编写代码实现
let person = [{ name: '张三', age: 30, sex: '男' },
{ name: '李四', age: 34, sex: '女' },
{ name: '小明', age: 12, sex: '男' }
]
var person2 = person.map(value => {
return {
...value,
age: value.age + 1
}
})
console.log(person2);
24.ES6中对字符串进行了哪些扩展
ES6中提供了模板字符串语法,可以让变量在字符串的内部使用其固定语法直接参与运算,优化了变量在字符串中的处理方式,同时ES6中针对字符串的常见操作提供了一些扩展函数如startWith()/endWith()/padStart()/padEnd()...
25.简述你对Symbol的认识
Symbol是ES6中出现的新的语法,表示一种获取唯一值对象的基本数据类型,经常用于模拟类型中私有属性而出现,如可遍历对象中的迭代器函数属性就是Symbol实现
26.简述var 和let声明变量的优缺点
var 是原生JS中声明变量推荐的方式,let是ES6语法中推荐的声明变量的方式,项目开发中优先推荐使用let声明并使用变量
var声明的变量最大的优点就是声明预解析,可以最大程度的保证声明的数据在其作用域空间中不会出现语法问题
let声明的变量最大的优点是明确了具体的作用域空间,同时强制确定了变量必须先声明后使用的规则,所以在新项目中使用优先推荐let关键词
27.for...of循环的本质是什么,如何让自己定义的类创建的对象支持for..of循环
for..of循环是ES6语法中提供的一种新的数据遍历语法,可以很方便的对比较集中的数据进行遍历操作,底层是通过Symbol定义的迭代器函数实现的
自定义类型如果要支持for..of循环遍历的功能,可以在类型中按照固定语法声明自定义的遍历函数[Symbol.iterator]实现遍历功能
28.简述原生JS面向对象和ES6新的面向对象语法的优缺点
原生JS本质上没有面向对象的独立的语法,主要通过函数结合原型链进行模拟的面向对象,在开发过程中的优缺点如下:
优点:语法简单,通过原生函数语法和原型链的操作直接实现,本质上是函数的扩展
缺点:思想上的转换,将函数当成类型使用,使用方式上和语法上都有一定的扩展,原生JS面向对象的实现方式上门槛较高
ES6语法中面向对象提供了独立的语法
优点:面向对象有自己独立的语法,可以很方便的完成面向对象的程序设计开发
缺点:新的语法学习成本提高了,底层的实现并没有进行重构,所以底层原理的理解上相比叫原生JS语法成本提高了
所以开发过程中如果JS用于浏览器一侧的效果开发,优先推荐函数式开发,如果是用于NodeJS的服务端的开发,优先推荐使用面向对象的语法开发
29.简述对ES6的认识
ES6是一种新的客户端脚本语言标准,语法上对原生JS进行了扩展,如提供了声明变量的let关键字和声明常量的const关键字,对函数进行了扩展,提供了箭头函数,函数参数默认值等,对对象进行了扩展提供了简洁操作语法,扩展了字符串操作函数,扩展了数组操作函数,扩展了Object操作函数等等,提供了class类和对象的新的语法标准等
30.var、let、const的区别
var是原生JavaScript中声明变量的关键字
let 是ES6中升级出现的声明变量的关键字,提供了块级作用域,出现了变量声明暂时性死区,限制了变量的多次声明等功能
const 是ES6语法中提供的用于声明常量的关键字
31.使用箭头函数的注意事项有哪些
箭头函数是ES6语法中出现的用于简化函数操作的一种新语法,使用的过程中需要注意内部this关键字的指向问题,需要注意语法中单个参数的简化语法,单行代码的情况下简化语法和返回值问题
32.使用解构赋值的操作语法,如何交换两个变量中的数据
let a = 1,b=2
[a,b] = [b,a]
33.call()\apply()\bind()有什么区别
call/apply/bind都可以改变this的指向,区别是参数的操作形式不同