函数的防抖:
- 概念: 如果一个事件被频繁执行多次,并且触发的时间间隔过短,则防抖函数可以使得对应的事件处理函数,只执行最后触发的一次. 函数防抖可以把多个顺序的调用合并成一次.
-使用场景:
- 搜索框输入: (只需要最后一次输入完成后再放松Ajax请求)
- 滚动事件Scroll:(只需要执行触发后的最后一次滚动事件的处理程序)
- 文本输入的验证: (连续输入文字后发送Ajax请求进行验证,停止输入后验证一次)
模拟百度搜索栏:
<div>
<input type="text">
<ul></ul>
</div>
<script>
// 获取标签对象:
const oIpt = document.querySelector('input');
const oUl = document.querySelector('ul');
// 设定变量存储延时器
let time = 0 ;
// 给input标签添加获取焦点事件
oIpt.addEventListener( 'focus' , () =>{
// 调用函数 获取数据 创建script标签 删除script标签
myJsonp();
})
// 给input标签添加输入数据事件
oIpt.addEventListener('input', () => {
// 触发执行生成延时器之前 先清除延时器
clearInterval( time );
// 通过延时器 调用执行 jsonp函数
time = setTimeout( ()=>{
// 调用函数 获取数据 创建script标签 删除script标签
myJsonp();
} , 1000 )
})
// 给input标签添加失去焦点事件
oIpt.addEventListener('blur' , ()=>{
oUl.style.display = 'none' ;
})
// jsonp函数
function myJsonp(){
// 获取input标签关键词
let keyword = oIpt.value ;
// 获取时间对象
const time = new Date();
// 创建 一个script标签对象
const s = document.createElement('script');
//createElement()括号里面只能有一个元素用引号括起来,因为javascript是动态代码,自由度很高,推荐用双引号,结束用分号。createElement()返回值是括号里面的元素节点。
// 设定script标签的src属性
s.setAttribute('src', `https://www.baidu.com/sugrec?pre=1&p=3&ie=utf-8&json=1&prod=pc&from=pc_web&wd=${keyword}&req=2&csor=2&pwd=1&cb=setPage&_=${time.getTime()}`);
//setAttribute() 方法添加指定的属性,并为其赋指定的值;
//这里利用setAttribute指定s的src属性,简单,很好理解。但是IE不支持,IE并不是不支持setAttribute这个函数,
//而是不支持用setAttribute设置某些属性,例如对象属性、集合属性、事件属性,也就是说用setAttribute设置style和onclick这些属性
//在IE中是行不通的。为达到兼容各种浏览器的效果,可以用点符号法来设置Element的对象属性、集合属性和事件属性。
// 在body标签的末位写入script标签
// 就等于是向百度数据接口发送了一个请求
document.body.appendChild(s);
// 请求执行结束 携带回响应体数据 script标签就可以删除
document.body.removeChild( s );
}
// 设定好一个函数 函数必须有一个形参
// 动态渲染生成页面函数
function setPage(result) {
console.log(result);
// result中 没有 g 属性 表示 没有对应的搜索结果
if( result.g === undefined ){
// ul标签是隐藏的效果
oUl.style.display = 'none';
// return终止之后程序的执行
return ;
}
// 根据 result.g 这个数组中 存储的对象数据 动态渲染生成页面
// item 是 数组中存储数据的对象
// item.q 是 对应的文字内容
let str = '' ;
result.g.forEach(item => {
str += `<li>${item.q}</li>`;
})
oUl.innerHTML = str;
oUl.style.display = 'block';
防抖说明: 输入 北京
/*
第一次触发输入事件 输入的是 b
clearInterval( time );
time存储的是 0 没有对应的延时器
time = setTimeout();
time存储1 对应的是 1秒以后执行的 b关键词的搜索,动态生成页面
第二次触发输入事件 输入的是 be
clearInterval( time );
time存储的是1 对应的是 b关键词延时器 就会被清除不执行 b关键词的搜索
time = setTimeout();
time存储2 对应的是 1秒以后执行的 be关键词的搜索,动态生成页面
第三次触发输入事件 输入的是 bei
clearInterval( time );
time存储的是2 对应的是 be关键词延时器 就会被清除不执行 be关键词的搜索
time = setTimeout();
time存储3 对应的是 1秒以后执行的 bei关键词的搜索,动态生成页面
重点:也就是在 延时器的延迟时间内
如果触发了新的操作
先清除上一个延时器 也就是 上一个输入的搜索不会执行
再生产一个新的延时器 执行 当前关键词收缩
*/
}
懒加载与函数的节流:
- 概念: 如果一个事件被频繁触发多次,节流函数可以按照固定的频率去执行相应的事件处理方法.函数节流保证一个事件一定时间内只能执行一次.
- -使用场景:
- DOM元素的拖拽功能实现(mousemove)
- 游戏中的刷新率
- Canvas画笔功能
- 总之,函数防抖适合多次事件一次响应的情况,函数节流适合大量事件按照时间做平均分配触发.