ES6-部分

搭配es6的笔记以及代码一起看,此处仅记录部分知识点

2、var和let和const

var a = [];
for (let i = 0; i < 10; i++) {
    a[i] = function () {
        console.log(i);
    };
}
a[6](); // 6

就是把函数的引用赋值给数组a,把函数存到数组里边,然后方便后边调用。
平常 var a = [1,2,3], 这次存的是 var a2 = [function1, function2, function3] 这样子,
调用 a[1],  a2[1]()即可调用其函数(下面的博客用了,偏门知识点

let 和 var 的区别_let var_违规昵称001的博客-CSDN博客

JavaScript let 和 const | 菜鸟教程

1.使用var声明的变量,其作用域为该语句所在的函数内,且存在变量提升现象;
2.使用let声明的变量,其作用域为该语句所在的代码块内,不存在变量提升;
3.let不允许在相同作用域内,重复声明同一个变量。

4.var重复声明变量时后面的会覆盖前面的。

5、补充:const 关键字来定义一个常量

function varTest() {
    var x = 1;
    if (true) {
        var x = 2;       // 同样的变量!
        console.log(x);  // 2
    }
    console.log(x);  // 2
}
function letTest() {
    let x = 1;
    if (true) {
        let x = 2;       // 不同的变量    
        console.log(x);  // 2  
    }
    console.log(x);  // 1,let声明的变量只能在其作用域内,两个x输出值不同
}

     //querySelectorAll() 方法返回文档中匹配指定 CSS 选择器的所有元素,返回 NodeList 对象。
    //NodeList 对象表示节点的集合。可以通过索引访问,索引值从 0 开始。

<ul>
   <li>11111</li>
   <li>2222</li>
   <li>3333</li>
</ul>
<script>
    var oli = document.querySelectorAll("ul li")
    //注意下面oli[i].onclick的事件方式
    for(var i=0;i<oli.length;i++){
        oli[i].onclick  =function(){
            //点击任意一个都是3,因为事件都是异步的,是先瞬间执行完for循环才去点击
            console.log(i)    
        }
    }

    for(let i=0;i<oli.length;i++){
        oli[i].onclick  =function(){
            //不同于上面,点击输出的是对应下标0、1、2
            console.log(i)
        }
    }
</script>

3、结构赋值

快速的从对象或者数组中取出成员的一个语法方式

 数组中的结构赋值:

//以前是arr[2]访问数组,现在结构赋值即a=1,b=2,c=3,顺序不可变,是一一对应的
let arr = [1,2,3]
let [a,b,c] = arr

//能更方便的交换数组、对象或者变量中元素的值,不需要第三者作为中间量,此时arr=[3,2,1]
arr = [c,b,a]
//普通变量还是需要放在数组中才能交换,此时x=2,y=1
let x = 1;      let y = 2;
[y,x] = [x,y];

//如何跳过部分元素只取第三个元素,此时a=3
let [,,a] =arr;

//如果数组内嵌套数组的写法,arr当中6不取就不写
let arr = [1,[2,3,4],5,6]
let [a,bb,c] = arr;     //bb=[2,3,4]
let [a,[b,,d],c] = arr;  //嵌套写法
console.log(b,d)//输出是2,4。

对象中的结构赋值:

//和数组的不同就是对象不是根据顺序来赋值,而是根据key值赋值,所以说顺序无所谓
//省略时也没有数组中后面的直接不写,前面的使用逗号替代的规则。直接全部不写即可
let obj = {
    name:"kerwin",
    age:100
}
let {age,name} = obj  //age=100,name="kerwin",类型分别是number和string
let {age} = obj

//先定义code,然后res对象内code不会和外面的code重复定义,但是下面变量赋值就会了
//所以说下面使用code:co表示把res内key值为code的值给co
//嵌套时如下面的data内的list即可
let code = "AAAA"
let res = {
    code:200,
    data:{
        list:["aaa","bbb","ccc"]
    }
}
//注意这嵌套关系用':'表示
let {data:{list:[x,y,z]},code:co,err="没有错误"} = res;
console.log(x,co,err)//输出aaa 200 '没有错误'
//项目中我们可以在前端接收后端数据的时候直接处理
//即把结构赋值的工作交给函数,并且在函数参数中赋值
function getData() {
    let res = {
        code: 200,
        data: {
            list: ["aaa", "bbb", "ccc"]
        }
    }
    test(res)  //调用函数处理
}
function test({code,data:{list}}){
    console.log(code,list)   //输出 200 和list整体
}
getData()

注意上面的嵌套关系

 4、模板字符串

map作用是映射调用此方法的数组,不会改变原始数组,返回原始数组每一项的操作,组成一个新数组,长度和原始数组一致
Array.map((item,index,arr)=>{
  //item => 数组的每一项
  //index => 数组每一项的索引
  //arr => 原数组
})

 结合笔记看,对于 `` 和""   ''   的区别不赘述

在 `` 当中,${}  内可以放置变量、表达式、复杂语句、函数等操作

//没写出的代码就是一个active的样式和<ul></ul>标签
function test(){
    return "函数返回结果"
}

let arr =["tiechui","kerwin","gangdan"]

//下面class当中的的语句是只让tiechui有样式,其他两个没有
let newlist = arr.map(function(item,index){
    return `<li class="${index===0?'active':''}">
        <b>${item}</b>
        ${test()}
        </li>`
})
console.log(newlist)

//querySelector获取第一个ul标签元素
let oul = document.querySelector("ul")
//不加join会在页面中每个数据间有逗号分隔(数组强行上页面默认是逗号分隔)
//join:把数组中的所有元素放入一个字符串,元素是通过指定的分隔符进行分隔的。
oul.innerHTML = newlist.join("")

4、字符串、数值、数组、对象扩展

(1)字符串扩展
let myname = "kerwin"
//ncludes函数判断字符串中是否存在指定字符,startsWith和endsWith是否已..开始或结束
//后面有参数是表示从下标0开始的第几个开始算,endsWith是从最后一个倒着来
 console.log(myname.includes("en"))
 console.log(myname.startsWith("er"))
 console.log(myname.endsWith("win"))

 console.log(myname.includes("e",1))
 console.log(myname.startsWith("e",1))
 console.log(myname.endsWith("r",3))

//repeat:返回一个新字符串,表示将原字符串重复n次。
 console.log(myname.repeat(2))  //kerwinkerwin
 console.log(myname.repeat(0)) //空
 console.log(myname.repeat(2.8))  //不合法,自动转化为2,kerwinkerwin
 console.log(myname.repeat("4"))  //传字符串如果是数还行:kerwinkerwinkerwinkerwin
(2)数值扩展
//isFinite:判断是否有限
let num1 = isFinite(100) //true
let num2 = isFinite(100/0) //false,100/0是无穷大
let num3 = isFinite(Infinity) // false, 无穷数分为正无穷(Infinity) 和负无穷(-Infinity)
let num4 = isFinite("100") //true, 会首先将字符串转为数字,能就是和上面一样的判断

let num1 = Number.isFinite(100) //true
let num2 = Number.isFinite(100/0) //false, 
let num3 = Number.isFinite(Infinity) // false
let num4 = Number.isFinite("100") //false,主要是这里不一样,Number.isFinite对于非数值类型的直接false
//isNaN()在接收到一个值之后,如果能成功转换则返回false,否则返回true;即非数字才是true
let num1 = isNaN(100) // false
let num2 = isNaN(NaN) //true
let num3 = isNaN("kerwin") //true
let num4 = Number.isNaN("100") // false

let num1 = Number.isNaN(100) // false
let num2 = Number.isNaN(NaN) //true
let num3 = Number.isNaN("kerwin") //false
let num4 = Number.isNaN("100") // false,和上面一样Number.isNaN不会转化直接判断

另外还有判断是否为整数的isInteger。Math.trunc将小数部分抹掉,返回一个整数。Math.sign方法用来判断一个数到底是正数、负数、还是零。对于非数值,会先将其转换为数值。

//Math.abs取绝对值,Number.EPSILON极小常量,非常小,无限趋向于0
//计算机中0.1+0.2不严格等于0.3,可能是0.300000000002
//isEqual函数就是判断两个数是否相等,即1两数之差是否无限小
function isEqual(a,b){
        return Math.abs(a-b)<Number.EPSILON
}

console.log(isEqual(0.1+0.2,0.3)) //true
console.log(0.1+0.2===0.3) //false,并不是严格相等的
(3)数组扩展

...     :    展开,理解为去掉数组中括号再合并的意思即可

arr.concat()  :  concat连接两个或多个字符串

arr.pop() : pop删除数组的最后一个元素并返回删除的元素

arr.shift() : shift把数组的第一个元素从其中删除,并返回第一个元素的值

都会直接改变原数组的值

let arr = [1,2,3]
//let arr2 = arr,传统赋值方法,改变arr2,必然导致arr改变,如下面删arr2的末尾元素时。
//利用concat或者是数组扩展便不会影响原数组,下面两行皆可
//let arr2 = arr.concat()
let arr2 = [...arr]
arr2.pop()     //要console.log(arr2.pop());才是输出的3

let arr3 = [4,5,6]
consolo.log([...arr,...arr3])   //输出[1,2,3,4,5,6],数组快速合并

 和之前的结构赋值一起用

let arr = [1,2,3,4,5,6,7,8]
//此时即a=1,b=2,c=3
let [a,b,c] = arr
//此时a=1,b=2,c=[3,4,5,6,7,8],...只能用在结构赋值最后
let [a,b,...c] = arr

Argument:能在没有形参的情况下,拿到实参的内容,也是一个类似于数组的方法

map  :创建一个新数组,这个新数组由原数组中的每个元素都调用一次提供的函数后的返回值组成。

Array.from :将类数组转换为真正数组,

//arguments虽然是吧获取到的实参变成了类数组,可以下标访问,但是不能用数组的方法,下面第二行报错
function test(){
  // console.log(arguments.filter)
  console.log(Array.from(arguments))
}
test(1,2,3,4)

//querySelectorAll和arguments一样,也是类数组结构,要转换1才能有要写数组方法
let olis = document.querySelectorAll("li")
// console.log(olis)
Array.from(olis).map(function(){

})

Array.of

新建数组,对之前旧方法Array的补充

let arr = [1,2,3]                //arr=[1,2,3]
let arr0 = Array(1,2,3)          //arr0=[1,2,3]
let arr1 = Array(3)              //arr1=[,,]即长度为3的空数组
let arr2 = Array.of(3)           //arr2=[1,2,3]
let arr3 = Array.of(1,2,3)       //arr3=[1,2,3]

 find

1)该方法主要应用于查找第一个符合条件的数组元素

2)它的参数是一个回调函数。在回调函数中可以写你要查找元素的条件,当条件成立为true时,返回该元素。如果没有符合条件的元素,返回值为undefined

let arr = [11,12,13,14,15]

//利用find返回值大于13的第一个数,输出14
let res = arr.find(function(item){
  return item>13
})
//利用find返回值大于13的第一个数的索引值,输出3
let res = arr.findIndex(function(item){
  return item>13
})
//利用find返回值大于13的最后一个数,输出15
let res = arr.findLast(function(item){
  return item>13
})
//利用find返回值大于13的最后一个数的索引值,输出4
let res = arr.findLastIndex(function(item){
  return item>13
})
console.log(res)

fill

使用自己想要的参数替换原数组内容,但是会改变原来的数组

//新建长为3的空数组,然后全部填充为即每个元素都是kerwin
let arr = new Array(3).fill("kerwin")

let arr1 = [11,22,33]
console.log(arr1.fill("kerwin"))       //不加参数默认全部变成kerwin
console.log(arr1.fill("kerwin",1,2))   //下标1到2之间的变成kerwin

flat()    flatMap()

按照一个可指定的深度递归遍历数组,并将所有元素与遍历到的子数组中的元素合并为一个新数组返回

//即扁平化处理,看例子即可
let arr = [1,2,3,[4,5,6]]
let arr1 = arr.flat()
console.log(arr1)    //输出[1,2,3,4,5,6],原数组arr未改变

let arr = [
  ["安庆","安阳","鞍山"],
  ["北京","保定","包头"]
]
console.log(arr.flat()) //输出["安庆","安阳","鞍山","北京","保定","包头"]

//上面的数据还不够复杂,项目中有可能是这样的要取所有城市放入一个数组中
//便需要flatMap的加入在回调函数中指定需要扁平化数组的具体位置
let arr = [
  {
    name:"A",
    list:["安庆","安阳","鞍山"]
  },
  {
    name:"B",
    list:["北京","保定","包头"]
  }
]
let res = arr.flatMap(function(item){
  return item.list
})
console.log(res)
(4)对象扩展

 不完全,可以看看笔记

扩展运算符:  ...    依然是三个点, ES2018新增

let obj = {
  name:"kerwin"
}
//用...把obj1展开在这里,此时obj1输出为{name:'kerwin'}
let obj1 = {
  ...obj
}
let obj2 = {
  age:100
}
let obj3 = {
  name:"tiechui"
}
//利用...合并上面的对象,就相当于打开{}大括号,直接把name、age的值放进去即可
//obj1和obj3都有name,合并时后面的会覆盖前面的,输出{name:'kerwin',age:100}
console.log({...obj1,...obj2,...obj3})

Object.assign     :ES6当中合并的方法,但是和上面ES2018的有所不同

Object.assign(target, object1,object2)的第一个参数是目标对象,后面可以跟一个或多个源对象作为参数。即会影响改变第一个参数的值(如果不想只有新建一个空对象作为第一个)

target:参数合并后存放的对象;      object1:参数1;      object2:参数2

const obj1 = {
    name: "kerwin"
};
const obj2 = {
    name:"tiechui"              //还是会覆盖前面的name值
};
const obj3 = {
    age:100
};
Object.assign(obj1, obj2, obj3);     //obj1输出 {name: 'tiechui', age: 100}
Object.is     :方法判断两个值是否是相同的值

==只判断值的相等          ===判断值和类型是否都相等之间(无法判断NaN是否相等)

NaN:not a number即非数字类型,Object.is弥补了===的缺陷

console.log(Object.is(5,5));
console.log(Object.is(5,"5"));
//parseInt函数可解析字符串,并返回一个整数,若字符串第一个字符不能转换为数字,那么返回NaN  
//可以判断返回的数据是否是NaN或者其他格式,作为检验返回数据格式是否正确 
console.log(Object.is(parseInt("kerwin"),NaN));

(5)函数扩展

参数默认值 

//即函数参数设置默认值,如果传来的参数不声明,就以默认为准
//url请求地址、get请求方法、async是否异步请求
function ajax(url,method="get",async=true){
  console.log(url,method,async)
}

ajax("/aaa","get",true)    //输出/aaa get true
ajax("/bbb")               //输出/bbb get true
ajax("/ccc","post")        //输出/ccc post true

rest参数 剩余参数:使用...替代即可

//即除了前面x,y所代表的1,2外,剩下的全部在data=[3,4,5,6]
function test(x,y,...data){
  console.log(data)
}
test(1,2,3,4,5,6)

箭头函数:写法简洁

语法: (函数的行参) => { 函数体内要执行的代码 }

//传统写法,定义函数test()
let test = function(){
}
//箭头函数写法
let test = ()=>{
}

现在把3、结构赋值中的模板字符串变为箭头函数

1、函数体只有一行代码的时候,可以不写 {},并且会自动 return

2、只有一个参数,可以省略()

3、如果返回的是对象需要注意,需要用()包起来

4、无法访问arguments,无法new,了解即可

let arr = ["aa","bb","ccc"]
let newlist = arr.map(function(item){
   return `<li>${item}</li>`
})
//箭头函数,函数主体只有return一句话,可以省略大括号和return
let newlist = arr.map((item)=>`<li>${item}</li>`)

//只有一个参数,可以省略()
let newlist = arr.map(item=>`<li>${item}</li>`)

//对象需要加()包起来,表示里面是一个对象
let test2 = () => ({
   name:"kerwin",
   age:100
})


箭头函数:this指向的是父作用域

普通函数:谁调用this,this就指向谁

oninput 事件在 <input> 或 <textarea> 元素的值发生改变时触发。oninput 事件 | 菜鸟教程

 注意下面,并不是任何时候都可以随便使用箭头函数的

<input type="text" id="mysearch">
</script> 
    let osearch = document.querySelector("#mysearch")

    osearch.oninput = function(){
        // console.log(this),
        //上面用的普通函数是因为改成箭头函数,这个this就指向父级,而父级就是window了
        //然后下面的setTimeout回调函数的this也指向这,然后也指向了window
        setTimeout(()=>{
            console.log(this.value)
            console.log(`发送${this.value}到后端,获取列表数据`)
        },1000)
    }
</script> 

5、Symbol

 2.3 ES6 Symbol | 菜鸟教程

ES6 引入了一种新的原始数据类型Symbol,表示独一无二的值。它属于 JavaScript 语言的原生数据类型之一,其他数据类型是:undefinednull、布尔值(Boolean)、字符串(String)、数值(Number)、对象(Object)。

 不难发现,之前对象当中的数据可能会在对象外被再次赋值而覆盖掉。Symblo可以解决这种事情

1、不能进行运行

2、不能

let s1 = Symbol() //生成了一个symbol类型数据
let s2 = Symbol()
console.log(s1 === s2)  //false

//不能进行各类运算包括字符串拼接,下面直接报错
console.log(s1>"aaaaa")

//可以隐式转化为boolean类型
if (s1) {
   console.log("执行")
}

6、Iterator

7、Set和Map

8、Proxy和Reflect

9、promise

回调地狱:在js的回调函数中,以下面的ajax请求为例,当aaa请求的数据需要传到bbb中,bbb的数据又需要传到ccc中,回调的层级关系太复杂,效率、易看性、后期修改都不方便,Promise便是为了解决此问题而出现。

function ajax(url, successcb, failcb) {
    setTimeout(() => {
        successcb("111111")
    }, 1000)
}
//以下都是输出111111
ajax("/aaa", function (data) {
    console.log(data)
    ajax("/bbb", function (data) {
        console.log(data)
        ajax("/ccc", function (data) {
            console.log(data)
        }, function () {

        })
    }, function () {

    })
}, function () {

})

Promise基本使用

new Promise(function (resolve, reject) {
  // resolve 表示成功的回调
  // reject 表示失败的回调
}).then(function (res) {
  // 成功的函数
}).catch(function (err) {
  // 失败的函数
})

//resolve和reject固定的参数,表示成功和失败,注意下方参数传递
let pro = new Promise(function(resolve,reject){
    //执行器函数
    setTimeout(()=>{
        //resolve(1000)       //此处成功和失败只能二取其一,都取以第一个为准
        //reject("no 1111")
    },1000)
})
//只有promis实例能够.then和.catch,分别表示resolve成功和reject失败应该执行的函数
//res和err是固定写法
pro.then((res)=>{
    console.log("奖金",res)    //输出   奖金 1000
}).catch((err)=>{
    console.log("没有",err)    //输出   没有 no 1111
})

Promise 实例具有如下三种状态:但是变化途径只有从“未完成”到“成功”从“未完成”到“失败”

异步操作未完成(pending
异步操作成功(fulfilled
异步操作失败(rejected

且一旦状态发生变化,就凝固了,不会再有新的状态变化,所以说上面resolve和reject即使同时存在也只以第一个为准

ajax简单示例:上面是定义的Promise实例,所以说能够使用.then这些东西,但是对于Ajax这些来说,需要自己return一个Promise对象,才能使得其结果能够使用.then和.catch,下面代码知识点有点多

属性描述
onreadystatechange存储函数(或函数名),每当 readyState 属性改变时,就会调用该函数。
readyState

存有 XMLHttpRequest 的状态。从 0 到 4 发生变化。

  • 0: 请求未初始化
  • 1: 服务器连接已建立
  • 2: 请求已接收
  • 3: 请求处理中
  • 4: 请求已完成,且响应已就绪
status200: "OK"
404: 未找到页面

 onreadystatechange_假易的博客-CSDN博客

 下面就根据条件不同区分了请求成功和失败的resolve和reject的代码

 请求文件如下:

//每当 readyState 改变时,就会触发 onreadystatechange 事件
function ajax(url){
    return new Promise((resolve,reject)=>{
        //下方是新建XMLHttpRequest对象操作,看上面知识点或者搜索一下
        //send就是直接send(),发送数据的意思
        let xhr = new XMLHttpRequest()
        xhr.open("get",url,true)
        xhr.send()
        xhr.onreadystatechange = function(){
            if(xhr.readyState===4){
                //200-300这个区间可以取看上面文章链接,是请求成功返回的代码
                if(xhr.status>=200&&xhr.status<300){
                    //responseText是后台返回的数据
                    //JSON.parse() 方法将数据转换为 JavaScript 对象
                    resolve(JSON.parse(xhr.responseText))
                }else{
                    reject(xhr.responseText)
                }
            }
        }
    })
}

ajax("1.json").then(res=>{
    console.log(res)
}).catch(err=>{
    console.log(err)
})

 .then链式调用:在.then当中

1、如果return 非promise类型,pending-fulfilled

2、如果return promise类型,根据这个新的promise对象的结果,决定pending-fulfilled或者 pending-rejected

总结:

        then 方法里面 return 一个返回值作为下一个 then 方法的参数,如果是 return 一个 Promise 对象,那么就需要判断它的状态

        即在.then当中,return非promise类型会直接把参数res传递给下一个.then

        如果return的promise类型,则看这个promise对象是成功还是失败,成功还是继续.then,失败则.catch

//从1.json请求的数据作为2.json的参数,即上面回调地狱的情况
//1和2.json可以正常请求,ajax()函数本来就是返回的promise数据,res则是非promise,下一个then可以直接得到
//下面输出的是: {data:11111}
//              {data:22222}
ajax("1.json").then(res=>{
    console.log(res)
    return ajax("2.json",res)
}).then(res=>{
    console.log(res)            
}).catch(err=>{
    console.log(err)
})

上面就是回调地狱解决方案:

 Promise.all()方法用于将多个 Promise 实例,包装成一个新的 Promise 实例。

Promise.race()方法同样是将多个 Promise 实例,包装成一个新的 Promise 实例。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值