一 、javaScript的特性
1.首先javascri是单线程的可以运行在浏览器或服务端的弱类型脚本语言
1.单线程
1.进程:完成一项任务所经历的的过程,一个进程可以包含多个线程
2.线程:线程比进程要小,一个线程只能属于一个进程
2.弱类型
变量的类型由赋值的类型决定
2.JavaScript的发展
1.JavaScript是1995年诞生
2.javaScript于2015发布EcmaScript2015(也称ES6)标准版本
3.跟踪ES最新技术进展的GitHub地址
官方文档:https://github.com/tc39/proposals/blob/master/finished-proposals.md
二、es6的一些常用的新特性
1.新增的const和let,以及const、let和var的三者区别
let、const、var都是声明变量的三种方式,以前只有var的时候容易存在变量使用混乱,比如变量会被重新定义覆盖,变量的提升也是不科学的,const就解决了这些问题。下面说下三者的具体区别在哪了。
1.看变量是否有提升
(1)三者中只有var是存在变量提升的,let和const都没有变量提升
变量提升就是var声明的变量会在js解析时提到代码坐在作用域的顶部提前声明,但是只是声明部分被提升,但是赋值的部分会留在原地,等代码执行到赋值才会被赋值,这也就造成了在同一作用域时,及时使用一个变量的代码块放在var声明的变量前面时也不会报错,只是获取不到变量值,但是变量可以被找到。
console.log(a);//输出结果undefined,可以找到变量a,但是拿不到a的值
var a=5;
console.log(a);//报错;初始化前无法访问,const也是同样
let a=5;
2.看是否有块级作用域
const和let都有自己的块级作用域,只在声明所在的块级作用域内有效。var没有块级作用域。
3.看是否可以可以重新定义
1.var可以重新定义和重新赋值
1.重新定义
var a= 15;
var a =54;//可以重新定义声明
2.重新赋值
var a=15
a=17//可以正常赋值
2.let 声明的变量可以重新赋值 但是不能重新定义
1.重新定义
let a= 15;
let a =54;//报错:a已经被声明
2.重新赋值
let a=15
a=17//可以正常赋值
3.const声明的变量不可以重新定义,也不可以重新赋值,const声明的变量为常量。
1.重新定义
const a=15;
const a=16;//报错:a 已经被声明
2.重新赋值
const a=2
a=4 //报错:常量不能重新赋值
2.变量的解构赋值
基本用法
ES6 允许按照一定模式,从数组和对象中提取值,对变量进行赋值,这被称为解构
1.从数组中解构赋值
(1)从数组中进行解构赋值时是按照结构内位置对应进行一一对应,进行赋值的,也可以说是等号两边的数组括号内的索引对应。并且要赋值的白能量要和数组使用一样的结构[ ]。
let [a,b,c]=[1,5,6]
console.log(a,b,c)//a=1,b=5,c=6
(2)当两边解构赋值时无法一一对应时,变量没有对应的时取到的结果为undefined。
let [a,b,c]=[1,5]
console.log(a,b,c)//a=1,b=5,c=undefined
(3)当结构的数组内的数据时数组或者对象时,依旧按照一维数组的结构位置对应进行赋值。
let [a,b,c]=[1,[5,6,8],{name:'lisi',age:'18'}]
console.log(a,b,c)
//a=1,b=[5,6,8],c={name:'lisi',age:'18'}
2.从对象中解构赋值
1.对象的解构与数组有一个重要的不同。数组的元素是按次序排列的,变量的取值由它的位置决定;而**对象的属性没有次序,变量必须与属性同名,才能取到正确的值。**使用和对象一样的结构{ }来放置要赋值的变量。
let {age,name}={name:'zhansan',age:'18'}
console.log(age,name)
//age='18',name='zhansan'
2.当取值的变量在解构的对象中没有的时候,就会解构失败,结果为undefined
let {aa,bb}={name:'zhansan',age:'18'}
console.log(aa,bb)
//aa=undefind,bb=undefind
3.如果自己不想使用对象中的属性名,使用自己定义的变量,可以通过下面这种重新赋值的方式进行解构赋值。
let {name:aa,age:bb}={name:'zhansan',age:'18'}
console.log(aa,bb)
//bb='18',aa='zhansan'
也就是说,是先找到同名属性,然后再赋给对应的变量。真正被赋值的是后者,而不是前者。
4.对象的解构赋值和数组的一样可以用于嵌套的关系,当对象的属性值也是一个对象的时候。
(1)直接去嵌套的属性值中是无法解构赋值,只能取到第一层的属性名。
let {name,age}={aa:{name:'zhansan',age:'18'}}
console.log(name,age)
//name=undefind,age=undefind
(2)如果想取到子级的属性值必须要带上对象的第一层的属性名。
let {aa:{name},aa:{age}}={aa:{name:'zhansan',age:'18'}}
console.log(name,age)
//name=张三,age=18
5.对象的解构也可以指定默认值。
(1)如果在对象的解构赋值中,对象中没有对应的属性名,也就是结果为undefind时,可以自己在等号左边指定默认值值。
var {x = 3} = {};
//x = 3
var {x, y = 5} = {x: 1};
//x = 1
//y = 5
(2)如果你指定默认值的变量在解构赋值中存在,不是undefind,那么你指定的默认值不会生效,解构赋值优先。
var {x = 3} = {x: 6};
//x =6
3.set和map:即数组和对象的升级版本
1**.Set是一种数据结构,类似于数组,但是它的成员都是唯一的,不能有重复的值,set本身也是一个构造函数,使用要用new’来生成set数据解构。**
(1)因为set数据的值时唯一的。所以可以用来去重。
let arr=new Set([3, 4, 5, 5, 2, 2, 4, 6, 562, 2])
console.log(arr)
被set实例化的数组后的数据都是唯一,解构类似于数组,但是没有length,set的时size来表示数据的个数。但是这样的去重数据解构会变成set数据结构。
(2)上面的方法对数组去重后数组数据解构的数据会变成set数据结构,下面这样去重可以解决这个问题。
var arr=[...new Set([2,5,6,8,9,55,5,6,8])]
console.log(arr)//输出的arr为数组。
(3).set的常用方法
(1)add:添加唯一值
(2) delete:删除某一个值
(3)clear:删除所有
(4)forEach:遍历set对象
2.ES6 提供了 Map 数据结构。它类似于对象,也是键值对的集合,但是“键”的范围不限于字符串,各种类型的值(包括对象)都可以当作键。
(1).map也是一个构造函数,使用的时候也需要new Map来实例化。
//m1.set(key,value)设置key的值
const obj=new Map()
obj.set(18,18)
console.log(obj)
//let m1=new Map() 创建map对象
const map = new Map([['name', '张三']]);
console.log(map)
(2) m1.get(key)获取key对应的值
(3) m1.keys()获取key所组成的对象
(4) m1.values()获取value组成的对象
(5)m1.entries()获取key,values组成的对象
(6)m1.forEach()遍历map对象
4.模块化
ES6 模块不是对象,而是通过export
命令显式指定输出的代码,再通过import
命令输入。
ES6的模块化:ES module
导出: export default {}
导入: import {},aa from ‘暴露的对象’
node里的模块化:commonJS
导出 modules.exports={}
导入 require(‘导入你的模块’)
5.扩展运算符(…)
扩展运算符(spread)是三个点( |
扩展运算符有两个作用,一个时展开操作,另一个是rest操作。
1展开操作
let arr=[5,5,6,56,6]
console.log(...arr)
//输出结果为:5 5 6 56 6
但是一个(…)扩展运算符只能展开一维数组,只能去掉一个[ ].
let arr=[5,5,[4,5,5],6,56,6]
console.log(...arr)
//输出结果为:5 5 (3) [4, 5, 5] 6 56 6
展开的特性也可以用来合并数组
let arr=[5,6,56,6]
let arr1=['zhansan','age']
console.log([...arr,...arr1])
//输出结果为:[5, 6, 56, 6, "zhansan", "age"]
同样可以拿来展开对象
var obj1={
name:'alice',
age:20,
address:'北京'
}
var obj2={
xueli:'本科',
hobby:'爬山'
}
console.log({...obj1,...obj2})
//输出结果为:{name: "alice", age: 20, address: "北京", xueli: "本科", hobby: "爬山"}
2.reset操作
在参数使用时,会把多的实参添加到数组中,多的实参是数组的每一项
let arr=[5,6,8,55,66]
function fn(a,...b){
console.log(a,b)
}
fn('zhansan',...arr)//输出:zhansan (5) [5, 6, 8, 55, 66]
6.箭头函数
格式:(参数1,参数2,…参数n)=>{ //代码块 }
普通函数和箭头函数区别
1.this指向不同:箭头函数没有自己的this,它的this指父级函数所在的this
2.箭头函数不能实例化:new ()=>{ } 报错
3.箭头函数没有arguments
7.模板字符串
js定义字符串的形式有3种:单引号(’ '),双引号(" "),反引号()
只有模板字符串可以使用变量
let a=18
let b=`我今年${a}`
console.log(b)//我今年18
8.数组和字符串新增的api方法:
字符串:
(1) str.includes(‘’) 检测字符是否有某个字符串,如果有返回true,否则false
(2) str.startsWith(‘’) 检测字符是否在字符串开始,如果是返回true,否则false
(3)str.endsWith(‘’)检测字符是否在字符串结尾,如果是返回true,否则false
数组:
(1) Array.from:可以将类对象转换成真正的数组
何为类数组:也称伪数组,看着像数组,但不具备数组的api方法,但伪数组有length属性,可以像真实数组那样通过下标来访问
真实数组 = Array.from(伪数组)
(2) Array.of()方法用于将一组值,转换为数组。
Array.of(3, 11, 8) // [3,11,8]
Array.of(3) // [3]
Array.of(3).length // 1
(3) 数组实例的find
方法,用于找出第一个符合条件的数组成员。它的参数是一个回调函数,所有数组成员依次执行该回调函数,直到找出第一个返回值为true
的成员,然后返回该成员。如果没有符合条件的成员,则返回undefined
let arr=[5,65,55,22]
console.log(arr.find(function(ele){return ele>40}))
//65 find()只会返回第一个符合条件的数组成员,一旦找到符合的就不会再执行后面的判断
(4) 数组实例的findIndex
方法的用法与find
方法非常类似,返回第一个符合条件的数组成员的位置,如果所有成员都不符合条件,则返回-1
。
let arr=[5,65,55,22]
console.log(arr.findIndex(function(ele){return ele<10}))
//0 返回的是符合条件的数组成员的索引
(5) flat:数组扁平化
数组的成员有时还是数组,Array.prototype.flat()
用于将嵌套的数组“拉平”,变成一维的数组。该方法返回一个新数组,对原数据没有影响。
[1, 2, [3, 4]].flat()
// [1, 2, 3, 4]
如果flat()没有参数只会拉平一层
[1, 2, [3, [4, 5]]].flat()
// [1, 2, 3, [4, 5]]
如果想要“拉平”多层的嵌套数组,可以将flat()
方法的参数写成一个整数,表示想要拉平的层数,默认为1
[1, 2, [3, [4, 5]]].flat(2)
// [1, 2, 3, 4, 5]