JavaScript 学习笔记(第五天)

JavaScript笔记

  • 一、正则表达式
    • 1.1、创建字符表达式
    • 1.2、元字符-基本元字符
    • 1.3、元字符-边界符
    • 1.4、元字符-限定符号
    • 1.4、元字符-特殊符号
    • 1.5、正则表达式-捕获exec
    • 1.6、正则表达式的两大特性
    • 1.7、正则与字符串方法
    • 1.8、案例-密码强度验证
  • 二、this
    • 2.1、this指向
    • 2.2、改变this指向
  • 三、ES6
    • 3.1、ES6介绍
    • 3.2、ES6关键词
    • 3.3、案例-块级作用域
    • 3.4、ES6的箭头函数
    • 3.5、ES6的解构赋值
    • 3.6、ES6的对象简写
    • 3.7、ES6展开运算符
    • 3.8、ES6模块化语法
  • 四、面向对象
    • 4.1、初始面向对象
    • 4.2、创建对象函数的方式
      • 4.2.1、构造函数的注意事项
    • 4.3、面向对象原型
    • 4.4、面向对象选项卡
    • 4.5、class类
    • 4.6、继承
    • 4.8、继承案例
    • 4.9、ES6继承
  • 五、初识前后端交互
    • 5.1、ajax
    • 5.2、案例:ajax
    • 5.3、ajax同步异步
    • 5.4、ajax的请求方式
    • 5.5、ajax封装
    • 5.6、回调地狱问题
    • 5.7、Promise封装ajax
    • 5.8、fetch
    • 5.9、闭包
    • 5.10、闭包案例

一、正则表达式

1.1、创建字符表达式

字面量的方式

var reg = /abc/
  • 此时可以检测一个字符串是否有一串紧密连接在一起的abc

内置构造函数

var reg = new RegExp ("abc")
  • 与上面效果相同

字面量有text()的方法,用于检测文字中是否含有输入的字面量

1.2、元字符-基本元字符

  1. \d代表着一位数字,即输入0~9之间的一位或以上的数字,写N个\d即为N个以上
  2. \D代表着一个非数字,即包含一个或以上,\Dk\D这种为中间必须有k而且是非数字
  3. \s代表着一位空白(空格 缩进 换行)有几个\s即为有几个空白
  4. \S代表着有一位非空白内容,有几个\S即为有几个非空白
  5. \n换行符
  6. \w包含字母,数字,下划线,有几个\w即为有几个字母,数字,下划线
  7. \W包含非(字母,数字,下划线),有几个\W即为有几个非(字母,数字,下划线)
  8. .任意内容(不包含换行)
  9. \转义字符,可将上述基本元素转换成普通字符

1.3、元字符-边界符

  • ^开头边界符
    • 放在\d前面即^\d,表示开头第一个字符必须是数字
  • $结尾边界符
    • 放在\d后米即\d$,表示结尾最后一个字符必须是数字
  • /^开头结尾$/
var reg = /^abc$/
  • 表示开头结尾必须是abc

1.4、元字符-限定符号

  • * 0~多次
    • 加在字符后面
  • + 1~多次
    • 加在字符后面,用exec方法可以截取出来数字的位置与长度
  • 0~1
    • 存在0个或者1个
  • {n}指定次数
    • 加载字符之后,限定他出现的次数,只能限定紧挨着的
  • {n,}大于等于n次
    • 加载字符之后,限定他出现的次数,必须大于等于n
  • {n,m}大于等于n小于等于m
    • 加载字符之后,限定他出现的次数,必须大于等于n小于等于m

1.4、元字符-特殊符号

  1. ()整体
    • 将限定的字符包括起来
    • 例:
      • /(abc){2}/
    • 这个就是限定出现两次abc
  2. |
    • 左右两边(整体)的都行
    • 例:
      • /a|b/
    • 有a或者有b都可以
  3. []代表一个
    • 中括号内中的字符有一个即符合
    • 有规律的可以用-来省略范围[a-z]表示从a到z,[0-9]表示从0到9,[a-zA-Z0-9_]就相当于\w
    • 例:
      • /[asdfgh]/
    • 输入的内容含有一位数与中括号内的相同,就是true
  4. [^]取反
    • 取不在这个括号范围内的数值,如果输入的值在这之中就算错误

1.5、正则表达式-捕获exec

  • 根据正则提取出一串字符串中的相关字符位置以及数量
  • 只能提取出遇到的第一个字符串
  • 捕获后返回的是一个数组

全局标识符g

  • 当一次行提取多个相同类型的变量时,可以通过在正则表达式后面加上g然后多次调用正则表达式来逐个提取出来
  • 给每个表达式加小括号后就会出现,先提取出所有大的组为数组的第0项,其次的后面的项是第0项依据正则表达式来得到的

标识符i

  • 忽略大小写
  • 例:/[a-z]/i
    • 没有i时代表着取得范围时a~z并且必须时小写,加上i之后大写也可以提取

1.6、正则表达式的两大特性

  1. 懒惰
  • 可以通过全局标识符g来解决
  1. 贪婪
  • 会将所要求提取的数据全部提取出来
  • 例:/\d{1,4}/
    • 当输入的值大于或等于四时,会提取出四个数值
  1. 非贪婪
  • 在正则表达式后加一个?
  • 例:/\d{1,4}?/
    • 只会会提取出来一个
  • ?对于限定范围内有效

1.7、正则与字符串方法

  1. replace
    • 替换字符串中的某个值
    • var newstr = str.replace(/a/g,"*")
      • 如果没有//g则只能提取出第一个a
  2. search
    • 查找字符串的位置
    • 只能查看第一个想要查看字符的位置
  3. match
    • 捕获内容
    • 当有重复的字符的字符串中,直接通过match与正则表达式,可以直接提取并且使其成为一个数组

1.8、案例-密码强度验证

var oinput= document.querySelector("input")
var ospan= document.querySelector("span")

var reg1 = /\d/
var reg2 = /[a-z]/
var reg3 = /[!@#$%^&*()]/

oinput.oninput  =function(){
	this.value
	var level =0
	
	if (reg1.test(this.value)) level++
	if (reg2.test(this.value)) level++
	if (reg3.test(this.value)) level++

	for(var i=0;i<=ospan.lenght;i++;){
		ospan[i].classList.remove("active")
		if(i<level){
			ospan[i].classList.add("active")
		}	
	}
}

二、this

2.1、this指向

  • 是JavaScript中的一个关键字
  • 谁调用this,this就指向谁(ES6 箭头函数)
  • 直接查看this,它是指向全局
  • 例子:
var obj = {
	name : "asdf"
	test : function(){
		console.log("111",this.name)
		}
	}
	obj.test()
//此时控制台出现的就是"111,asdf"

2.2、改变this指向

  1. call
    • 可以改变call()指向括号内部的值
    • 可以传n个参数
    • 执行函数,并改变this执行为函数的第一个参数
  2. apply
    • 执行函数,并改变this执行为函数的第一个参数
    • 支持两个参数,第二个参数是数组
  3. bind
    • 改变this执行为函数的第一个参数,不会自动执行函数

三、ES6

3.1、ES6介绍

  • 我们所说的ES5和ES6其实就是在js语法的发展过程中的一个版本而已
  • ECMAScript就是js的语法
    • 以前的版本没有某些功能
    • 在ES5这个版本的时候增加了一些功能
    • 在ES6这个版本的时候增加了一些功能
  • 因为浏览器是浏览器厂商生产的
    • ECMAScript 发布了新的功能以后,浏览器厂商需要让自己的浏览器支持这些功能
    • 这个过程是需要时间的
    • 所以到现在,基本上大部分浏览器都可以比较完善的支持了
    • 只不过有些浏览器还是不能全部支持
    • 这就出现了兼容性问题
    • 所以我们写代码的时候就要考虑哪些方法是ES5或者ES6的,看看是不是浏览器都支持

3.2、ES6关键词

  1. let
    • 定义变量
    • 必须先定义在使用, 使用必须在定义之后
    • 一个变量名称只能定义一次
    • 定义的变量只在一个块级作用域(相当于在一个大括号内)
  2. const
    • 定义常量
    • 定义后不能变,并且使用comst必须赋值

3.3、案例-块级作用域

var oHeaderItems = document.querySelectorAll(".header li")
var oBoxItems = document.querySelectorAl1( ".box li")
	for(let i=0; i<oHeaderItems.length; i++){
		oHeaderItems[i].dataset.index = i	
		oHeaderItems[i].onclick = function(){
		}
	}
  • 选项卡案例改编,let定义后可以使当前的值得以保留所以每次点击都是当前的值,而不是循环后的值

3.4、ES6的箭头函数

  • 相当于将function(){}改变成了()=>{}

特点

  1. 可以省略括号(只能是只有一个形参时可以省略)
  2. 可以省略{}(只有返回值时可以省略return,只有一句代码时)
  3. 当返回一句语句,并且是对象时,需要在大括号外面加一个括号
  4. 没有arguments(arguments是相当于没有形参时,但传入了参数,此时可以以数组的方式查看参数)
  5. 箭头函数没有this,箭头函数中的this会指向父级作用域

默认参数
在函数的形参区域先给参数定义一个值

3.5、ES6的解构赋值

  • 快速的从对象和数组中获取里面的成员
  • 例:
var arr = ["asd","132","12sd"]

let [x,y,z]

console.log(x,y,z)
  • 交换:
var a = 10
var b = 20
var [b,a] = [a,b]
  • 多维数组取值:
var arr = [1,2,[3,4,[5]]]

//想获取5,需要arr[2][2][0]
var [a,b,[c,d,[e]]] = arr

//直接取e即可

对象

  • 赋值对象(对号入座)
var obj = {
	name = "zhangsan"
	age = 100
	location:"henaN"
}

let {name , age, location:mylocation} = obj

3.6、ES6的对象简写

对象结构中,key与后面的变量相同时,可以不写变量的名称

mybtn.onclick = function(){
	let usesrname = myusername.value
	let password = password.value

	var obj = {
		username,
		password
	}
}

3.7、ES6展开运算符

  • ...展开运算符

  • 展开数组

    • 可以展开数组
    var a = [1,2,3]
    var b = [2,3,4,5]
    var c = [...a...b]
    //此时c数组等与a与b数组合并
    
    • 可以复制数组
    arr a = [1,2,3]
    var b = [...a]
    
    • 参数-实参-形参
    var test = (...arr)=>{
    	console.log(arr)
    }
    test(1,2,3,4,5)
    
    • 提取数组最大值
    var arr = [1,2,3,4,5]
    
    var res = Math.max(...arr)
    
    • 伪数组转换
    function test(){
    	var arr  = [...arguments]
    }
    test(1,2,3,4,5)
    
  • 展开对象

    • 合并对象
    var obj1 = {
    	name:"zhangsan"
    	age:100
    }
    var obj1 = {
    	name:"zhangsan"
    	age:100
    }
    
    var obj = {
    ...obj1,
    ...obj2
    }
    //出现相同的key时下面的会覆盖掉上面的
    

3.8、ES6模块化语法

  1. 私密不漏

    • 为了防止不想被看见的函数被使用,在js文件中将想被表达的函数放在export{}中,以对象的方式
    • 然后在原文件里的script里的type中添加module,紧接着用import{}from './module/XXX'的 { }中加入export{}中的方法
  2. 重名不怕

    • 与上面的方法相同,如果出现了相同的函数,则会报错
  3. 依赖不乱

    • 在哪里用函数就在哪里导入函数,可以避免未定义而提前用

四、面向对象

4.1、初始面向对象

  1. 首先,我们要明确,面向对象不是语法,是一个思想,是一种 编程模式
  2. 面向: 面 (脸) ,向 (朝着)
  3. 面向过程: 脸朝着过程 =》关注着过程的编程模式
  4. 面向对象:脸朝着对象=》关注着对象的编程模式实现一个效果
  5. 实现一个效果
    • 在面向过程的时候,我们要关注每一个元素,每一个元素之间的关系,顺序,。。。
    • 在面向过程的时候,我们关注的就是找到一个对象来帮我做这个事情,我等待结果
  6. 我们以前的编程思想是,每一个功能,都按照需求一步一步的逐步完成

4.2、创建对象函数的方式

  1. 工厂函数:
 function createObject(name){
            var obj = {}
            obj.name = name
            //if(name==XXX){执行XXX}
            onj.matical = []
            return obj
        }
        var obj1 = createObject('shaokao')
  1. 自定义函数
            function createObject(name){
                this.name = name
                this.martical = []
                this.coke = function(){
                     
                }
            }

            var obj2=new createObject("第三次")

4.2.1、构造函数的注意事项

  1. 首字母大写

    • 例:
    • function CreateObject(){}
  2. 构造函数中不写return

  3. 构造函数可以当成不同函数用,不过里面加了this会指向window

  4. this指向

            function createObject(name){
                this.name = name
                this.martical = []
                this.coke = function(){
                     
                }
            }
            new CreateObj()//new过程 == 实例化这个过程,实例化后,,this指向实例化对象

4.3、面向对象原型

概念:

  • 在典型的 OOP 的语言中(如 Java),都存在类的概念,类就是对象的模板,对象就是类的实例,但在 ES6之前, JS 中并没用引入类的概念。
  • ES6, 全称 ECMAScript 6.0 ,2015.06 发版。但是目前浏览器的 JavaScript 是 ES5版本,大多数高版本的浏览器也支持 ES6,不过只实现了 ES6 的部分特性和功能。
  • 在 ES6之前 ,对象不是基于类创建的,而是用一种称为构造函数的特殊函数来定义对象和它们的特征。

对象原型__proto__

  • 对象都会有一个属性__proto__指向构造函数的prototype原型对象,之所以我们对象可以使用构造函数prototype原型对象的属性和方法,就是因为对象有__proto__原型的存在。
  • __proto__对象原型和原型对象prototype是等价的。
  • __proto__对象原型的意义就在于为对象的查找机制提供一个方向,或者说一条路线,但是它是一个非标准属性,因此实际开发中,不可以使用这个属性,它只是内部指向原型对象prototype

4.4、面向对象选项卡


<head>
	<style>
	*{
	margin:0;
	padding:0;
	}
	ul{
	list-style: none;
	}
	.header{
	dispLay: flex;
	width:500px;
	}
	.header li {
	flex:1;
	height: 50px;
	line-height: 50px;
	text-align: center;
	border:1px solid black;
	}
	.box {
	position: relative;
		height: 200px;
	}
	.box li {
	position: absolute;
	left:0;
	top:0;
	width: 500px;
	height: 200px;
	background-color:yellow;
	display:none;
	}
	.header .active{
	background-color: red;
	}
	.box .active{
	dispLay: block;
	}
	</style>
</head>
<body>
	<div class="container1">
		<ul class=" header">
		<li class="active">1</li>
		<li>2</li>
		<li>3</li>
		<li>4</li>
	</ul>
	</div>
	<div class="container2">
	<ul class="box">
		<li class="active">111</li>
		<li>222</li>
		<li>333</li>
		<li>444</li>
	</ul>
	</div>
<script>

		function Tabs(select,type){
			var container = document.querySelector(select)
			this.oHeaderItems = container.querySelectorAll(".heraer li")
			this.oBoxItems = document.querySelectorAl1( ".box li")
			this.type = type
			this.change()
}
	Tabs.prototype.change = function(){
	for(let i=0; i<oHeaderItems.length; i++){
		this.oHeaderItems[i].addEventListener(type,()=>{
		var index =i
		for(var m=0;m<oHeaderitems.length; m++){
			this.oHeaderItems[m].classList.remove("active")
			this.oBoxItems[m].classList.remove( "active")
		}
			this.oHeaderItems[index].classList.add( "active")
			this.oBoxItems [index].classList.add ( "active")
		})
	}
}

	new Tabs(".container1","click")
	new Tabs(".container2","mouserover")
</script>
</body>


4.5、class类

cLass createobj {
//构造器函数
constructor( name){
	this.name =name
	}
}

4.6、继承

  1. 构造函数继承
function Person(name,age){
		this.name = name
		this.age = age
	}
	Person.prototype.say = function(){
	console.log(this.name,this.age)
}
	function student(name,age,classroom){
		Person.call(this,name,age)
		this.classroom = classroom
	}
  1. 原型继承
	student.prototype = new Person()
  1. 组合继承
    构造函数继承+原型继承
function Person(name,age){
		this.name = name
		this.age = age
	}
	Person.prototype.say = function(){
	console.log(this.name,this.age)
}
	function student(name,age,classroom){
		Person.call(this,name,age)
		this.classroom = classroom
	}

	student.prototype = new Person()
        
    var obj1 = new student("lu",18,474)
        console.log(obj1)
        obj1.say()

4.8、继承案例

<div class="box1">
	<h1></h1>
	<ul></ul>
</div>
<div class="box2">
	<h1></h1>
	<img src="">
	<ul></ul>
</div>
<script>

var data1 = {
	title: "体育",
	list:["体育-1","体育-2","体育-3"]
}
var data2 = {
	title:"综艺",
	url:""
	list:["综艺-1","综艺-2","综艺3"]
}
function CreateList(select,data={}) {
	this.ele = document.queryselector(select)
	this.title = data.title,
	this.list = data.list
}
CreateList.prototype.render = function () {
//渲染页面
	var h1 = this.ele.querySelector("h1")
	var ul = this.ele.querySelector("ul")
	// console.log(h1,ul)
	h1.innerHTML = this.title
	ul.innerHTML = this.list.map(item => `
  • ${item}
  • `
    ).join("") } var obj1 = new CreateList( ".box1", data1) obj1.render() function CreateImgList(select,data){ CreateList.call(this,select,data) this.imgUrl = data.url } CreateImgList.prototype = new CreateList() CreateImgList.prototype.enhenceRender = function(){ this.render() var img = this.ele.querySelector("img") img.src = this.imgUrl } var obj2 = new CreateImgList( ".box2" , data2) obj2.enhenceRender() <script>

    4.9、ES6继承

      //父类
            class Person{
                constructor(name,age){
                    this.name = name
                    this.age = age
                }
                say(){
                    console.log("hello")
                }
            }
    		//子类
            //extends继承
            class Student extends Person{
                constructor(name,age,grade){
                    super(name,age)
                     //super相当于Person.call(this,name,age).而且super必须写到constructor里面的第一行
                    this.grad = grade
                }
                //直接可以改变Parson里面的方法使自己使用
                
                say(){
                    super.say()//调用父元素的say()使其不会被覆盖
                    document.write("bjsad")//修改say()方法,将其覆盖,若加上super就不会被覆盖
                }
            }
    
            var obj = new Student("asd",100,100)
            console.log(obj.grad)
            obj.say()
    

    五、初识前后端交互

    5.1、ajax

    AJAX 的优势

    1. 不需要插件的支持,原生js 就可以使用
    2. 用户体验好(不需要刷新页面就可以更新数据)
    3. 减轻服务端和带宽的负担
    4. 缺点: 搜索引擎的支持度不够,因为数据都不在页面上,搜索引擎搜索不到

    AJAX 的使用

    1. 在js 中有内置的构造函数来创建 ajax 对象
    2. 创建 ajax 对象以后,我们就使用 ajax 对象的方法去发送请求和接受响应

    创建步骤:

    1. 创建XHR ==>new XMLHttpRequest()
    2. 配置open(请求方式,请求地址,是否同步)
    3. send发出
    4. 接受数据,创造一个事件

    ajax状态码 200 ok 404 error

    • ajax 状态码-xhr.readyState
    • 是用来表示一个 ajax 请求的全部过程中的某一个状态
      • readyState === 0:表示未初始化完成,也就是open方法还没有执行
      • readyState ===1:表示配置信息已经完成,也就是执行完open 之后
      • readystate === 2 : 表示send 方法已经执行完成
      • readystate === 3 :表示正在解析响应内容
      • readystate === 4 :表示响应内容已经解析完毕,可以在客户端使用了
    • 这个时候我们就会发现,当一个 ax请求的全部过程中,只有当 readystate === 4 的时候,我们才可以正常使用服务端给我们的数据 所以,配合 http 状态码为 200 ~ 299
    • 一个ajax 对象中有一个成员叫做 xhr.status这个成员就是记录本次请求的 http
    • 状态码的两个条件都满足的时候,才是本次请求正常完成
      var xhr = new XMLHttpRequest()
          // ip:js%E5%AE%9E%E6%88%98%E7%BB%83%E4%B9%A0
            xhr.open("GET","http://127.0.0.1:5500/js%E5%AE%9E%E6%88%98%E7%BB%83%E4%B9%A0/01.text")
            xhr.send()
    
            //当后端与前端接上头后执行该函数
            xhr.onreadystatechange = function(){
                // console.log("edkw");
    
                if(xhr.readyState===4 &&xhr.status === 200){
                    console.log("此时已经加载完毕");
                }else if(xhr.readyState === 4 &&xhr.status===404){
                    console.log("没有找到这个对象");
                }
            }
            //两种区别为:onload判断一次,而onreadstatechange判断四次
             xhr.onload = function(){
                  console.log(xhr.responseText)
               if(xhr.status==200){
                   document.write(xhr.responseText)
                }else if(xhr.status===404){
                     console.error("没有找到这个页面")
                      location.href ="404.html
                 }
             }
    

    readyStateChange

    • 在ajax对象中有一个事件,叫做readystatechange事件
    • 这个事件是专门用来监听ajax对象的readystate值改变的的行为
    • 也就是说只要readystate的值发生变化了,那么就会触发该事件
    • 所以我们就在这个事件中来监听ajax的readystate是不是到4了
    const xhr = new XMLHttpRequest(
    xhr.open( 'get', './data.php ')
    
    xhr.send()
    
    xhr.onreadystatechange = function(){
    	//每次readystate改变的时候都会触发该事件
    	//我们就在这里判断readystate的值是不是到4
    	//并且 http的状态码是不是200 ~ 299
    	if (xhr.readystate === 4&&/^2\d{2|S$/.test(xhr.status)) {
    	//这里表示验证通过
    	//我们就可以获取服务端给我们响应的内容了}
    	```
    	}
    }
    

    5.2、案例:ajax

    JavaScript部分

    <ul id="malist"></ul>
        <button id="btn">lisy</button>
        <script>
            btn.onclick = function(){
                var xhr = new XMLHttpRequest()
                // ip:js%E5%AE%9E%E6%88%98%E7%BB%83%E4%B9%A0
                    xhr.open("GET","http://127.0.0.1:5500/js%E5%AE%9E%E6%88%98%E7%BB%83%E4%B9%A0/data.json")
                    xhr.send()
    
                    //当后端与前端接上头后执行该函数
                    xhr.onreadystatechange = function(){
                        // console.log("edkw");
    
                        if(xhr.readyState===4 && xhr.status === 200){
                            console.log("此时已经加载完毕");
                            var jsondata = JSON.parse(xhr.responseText)
                            rader(jsondata)
                        }else if(xhr.readyState === 4 && xhr.status===404){
                            console.log("没有找到这个对象");
                        }
                    }
                function rader(jsondata){
                    var html = jsondata.data.list.map(item=>`
                        
  • ${item.imageUrl}"/>
    ${item.name}
  • `
    ) malist.innerHTML = html.join('') } }

    json部分

    {
        "data":{
            "list":[
                {
                    "namne":"1111",
                    "imageUrl":"https://ts1.cn.mm.bing.net/th?id=ORMS.7bf3e9347df69e68f66692e0f32f7bc9&pid=Wdp&w=612&h=304&qlt=90&c=1&rs=1&dpr=1.25&p=0"
                    
                },
                {
                    "namne":"1111",
                    "imageUrl":"https://ts1.cn.mm.bing.net/th?id=ORMS.7bf3e9347df69e68f66692e0f32f7bc9&pid=Wdp&w=612&h=304&qlt=90&c=1&rs=1&dpr=1.25&p=0"
                    
                },
                {
                    "namne":"1111",
                    "imageUrl":"https://ts1.cn.mm.bing.net/th?id=ORMS.7bf3e9347df69e68f66692e0f32f7bc9&pid=Wdp&w=612&h=304&qlt=90&c=1&rs=1&dpr=1.25&p=0"
                    
                }
            ]
        }
    }
    

    5.3、ajax同步异步

    通过里面的第三个参数判断

    xhr.open("GET","地址",true)
    

    true 表示异步请求:表示会进行后面的函数,等返回值调回来的时候跟着回去
    false表示同步请求:要等到返回的数据回来过后才会执行后面的代码,所以容易造成数据的堵塞

    5.4、ajax的请求方式

    get 偏向获取数据
    post 偏向提交数据
    put 偏向更新(全部)
    delete偏向删除信息
    patch 偏向部分修改

    1. get
    const xhr = new XMLHttpRequest();
    //设置响应体数据类型
    xhr.responseType='json'
    xhr.open('GET','http://127.0.0.1:8080/server-json /*?(传参位置,可以获取想得到的数据,如果不加就是全部取出 例:username=ximen)*/ ')
    xhr.send()
    xhr.onreadystatechange=function(){
        if(xhr.readyState===4){
            if(xhr.status >= 200 ){
             console.log(xhr.response);
             
              }
         }
    } 
    
    1. post
    const xhr = new XMLHttpRequest();
    //设置响应体数据类型
    xhr.responseType='json'
    xhr.open('POST','http://127.0.0.1:8080/server-json')
    xhr.send()
    xhr.onreadystatechange=function(){
       if(/^2d{2|$/.test(xhr.status){
            if(xhr.status >= 200 ){
             console.log(JSON.parse(xhr.responseText));
              }
         }
    	//如果是POST形式的需要添加send在后面
    	//支持 name=Kerwin&&age=100的方式
    	//还支持{"name":"asd"}的方式
    	xhr.setRequestHeader( "content-Type","application/-www-form-urlencoded")//name=kerwin&age=100
    	xhr.send(`username=gangdaner&password=123`)
    	
    	xhr.setRequestHeader( "content-Type","application/json")//json字符串方式
    	xhr.send ( JSON.stringify({
    	username: "ximen",
    	password: "789"}))
    } 
    
    1. put
    xhr.responseType='json'
    xhr.open('PUT','http://127.0.0.1:8080/server-json/1')
    xhr.send()
    xhr.onreadystatechange=function(){
       if(/^2d{2|$/.test(xhr.status){
            if(xhr.status >= 200 ){
             console.log(JSON.parse(xhr.responseText));
              }
         }
    	xhr.setRequestHeader( "content-Type","application/-www-form-urlencoded")//name=kerwin&age=100
    	xhr.send(`username=111111`)
    	
    	xhr.setRequestHeader( "content-Type","application/json")//json字符串方式
    	xhr.send ( JSON.stringify({username: "111",)
    }
    
    1. patch
    const xhr = new XMLHttpRequest();
    //设置响应体数据类型
    xhr.responseType='json'
    xhr.open('PATCH','http://127.0.0.1:8080/server-json/2')
    xhr.send()
    xhr.onreadystatechange=function(){
       if(/^2d{2|$/.test(xhr.status){
            if(xhr.status >= 200 ){
             console.log(JSON.parse(xhr.responseText));
              }
         }
    	//支持 name=Kerwin&&age=100的方式
    	//还支持{"name":"asd"}的方式
    	xhr.setRequestHeader( "content-Type","application/-www-form-urlencoded")//name=kerwin&age=100
    	xhr.send(`username=adasdasd`)
    	
    	xhr.setRequestHeader( "content-Type","application/json")//json字符串方式
    	xhr.send ( JSON.stringify({username: "asdasda"}))
    } 
    
    1. delete
    const xhr = new XMLHttpRequest();
    //设置响应体数据类型
    xhr.responseType='json'
    xhr.open('DELETE','http://127.0.0.1:8080/server-json/1')
    xhr.send()
    xhr.onreadystatechange=function(){
       if(/^2d{2|$/.test(xhr.status){
            if(xhr.status >= 200 ){
             console.log(JSON.parse(xhr.responseText));
              }
         }
    	send()
    } 
    
    

    5.5、ajax封装

    function queryStringify(obj){
    	let str = ''
    	for (let k in obj)str += `${k}=${obj[k]}&`	
    	return str.slice(0,-1)
    }
    function ajax (options){
    		let defaultoptions = {
            ur1:"http://1ocalhoscct:3000/users",
            method:"GET",
            async:true ,
            data:{
            username : "kerwin",
            password:"123"
            },
            headers:{},
            success:function(res){
                console.log(res)
            }
            error:function(err){
                console.log(err)
            }
        })
    

    5.6、回调地狱问题

    • 当一个回调函数嵌套一个回调函数的时候·就会出现一个嵌套结构
    • 当嵌套的多了就会出现回调地狱的情况·比如我们发送三个ajax请求
    • 第一个正常发送
    • 第二个请求需要第一个请求的结果中的某一个值作为参数
    • 第三个请求需要第二个请求的结果中的某一个值作为参数

    5.7、Promise封装ajax

    <script>
    封装 ajax
      function ajax(options) {
        let defaultoptions = {
          url: "",
          method: "GET",
          async: true,
          data: {},
          headers: {
            "content-type":"application/x-www-form-urlencoded"
          },
          success: function () { },
          error: function () { }
        }
        let { url, method, async, data, headers, success, error } = {
          ...defaultoptions,
          ...options
        }
        </script>
    
    
    

    5.8、fetch

    用于发起获取资源的请求。它返回一个 promise,这个 promise 会在请求响应后被 resolve,并传回 Response对象。当遇到网络错误时,fetch() 返回的 promise 会被 reject,并传回 TypeError。成功的 fetch()检查不仅要包括 promise 被 resolve,还要包括 Response.ok 属性为 true。HTTP 404状态并不被认为是网络错误。

    var username = "kerwin"
    fetch(` http:// localhost:3000/users111?username=$ {username} `)
    .then((res)=>{
    console. log(res)
    if(res.ok){
    return res.json()
    }else{
    //拒绝
    return Promise.reject(
    }
    
    

    cookie

    <script>
           //cookie 本地存储
           // 存cookie
    
           savebtn.onclick = function(){
               //路径设置
            //    document.cookie = "username=xiaoming;path=/155-cookie/aaa"
                document.cookie = "age=18"
           
                //过期时间设置
                var date = new Date()
                date.setMinutes(date.getMinutes()+10)
                document.cookie = `username=kerwin;expires=${date.toUTCString()}`
            }
    
            getbtn.onclick = function(){
                console.log(getCookie("age"))
            }
    
            function getCookie(key){
                var str = document.cookie
                var arr = str.split("; ")
                // console.log(arr)
                var obj = {}
                for(var i=0;i<arr.length;i++){
                    var subArr = arr[i].split("=")
                    // console.log(subArr)
                    obj[subArr[0]] = subArr[1]
                }
    
                // console.log(obj)
                return obj[key]
            }
    
            delbtn.onclick = function(){
                var date = new Date()
                date.setMinutes(date.getMinutes()-1)
                document.cookie = `username=111;expires=${date.toUTCString()}`
                document.cookie = `age=111;expires=${date.toUTCString()}`
            }
    </script>
    

    josnp
    注:

    1. 后端接口形式必须**(),需要后端配合
    2. jsonp 缺点
      onload 删除sciprt标签
      只能get请求,不能post put delete
    mybtn.onclick = function(){
    var oscript = document.createElement( "script")
    oscript.src="01.txt”//未来地址
    document.body . appendchild(oscript)
    }
    
    
    
    

    5.9、闭包

    函数内部返回一个函数,被外界所引用。
    这个内部函数就不会被销毁回收。
    内部函数所用到的外部函数的变量也不会被销毁

    5.10、闭包案例

    求索引值下标
    法一:(闭包)

    var oli = document.querySelectorAl1("li")
            for (var i = 0; i < oli.length; i++) {
                oli[i].onclick = (function (index) {
                    return function () {
                        console.log(11111, index)
                    }
                })(i) //匿名自执行函数
            }
    
    

    法二:(ES6)

     var oli = document.querySelectorAl1("li")
            for(let i=0;i<oli.length;i++){
                oli[i].onclick =function(){
                    console.log(i)
                }
            }
    
    

    你可能感兴趣的:(JavaScript,javascript,正则表达式,java)