jQuery中借助deferred来请求及判断AJAX加载的实例讲解


Posted in Javascript onMay 24, 2016

ajax请求异步队列加载
我们在开发程序的时候通常会碰到使用ajax加载数据显示到列表的情况。ajax默认使用异步加载(async:true)。为什么不使用同步呢,因为ajax同步加载会UI渲染线程阻塞的问题。通常表现为在加载大量数据时由于加载时间过长导致页面不能点击、gif动画卡死以及浏览器崩溃等问题。所以,一般情况下,尽量使用ajax异步加载。
可是,我们有些时候的需求要求ajax同步加载,一个加载完再加载下一个,即所谓的队列。前面我们有说过,同步加载会引起UI渲染阻塞问题。那么我们要怎么实现顺序加载而不引起该问题呢?
示例代码一:

<script src="http://libs.baidu.com/jquery/2.0.0/jquery.min.js"></script>
<script>
$(function(){
 $("#clickBtn").on("click",function(){
  getData(0,10);//输出0-9
 })
})

function getData(i,length){
 $.ajax({
  type:"post",
  url:"setDeffer.php",
  data:{
   data:i
  },
  async:true,//异步
  success:function(data){
   $("#showArea").text($("#showArea").text()+data+"\n");
   if(i<length-1){
    getData(i+1,length);
   }
  }
 });
}
</script>

PHP后台代码:

<?php
$str = $_POST["data"];
sleep(1);//延迟1秒
echo "输出".$str;
?>

当然,jquery也提供了我们deferred对象来解决回调函数的问题。
示例代码二:

<script src="http://libs.baidu.com/jquery/2.0.0/jquery.min.js"></script>
<script>
$(function(){
 $("#clickBtn").on("click",function(){
  recycleData(0,10);//输出0-9
 })
})

function getData(i){
 var defer = $.Deferred();
 $.ajax({
  type:"post",
  url:"setDeffer.php",
  data:{
   data:i
  },
  async:true,//异步
  success:function(data){
   $("#showArea").text($("#showArea").text()+data+"\n");
   defer.resolve(data);
  }
 });
 return defer.promise();
}
function recycleData(i,length){
 $.when(getData(i)).done(function(data){//这里的data为defer在ajax保存下来的数据
  if(i<length-1){
   recycleData(i+1,length);//递归
  }
 })
}
</script>

这里首先创建一个deffered对象,在ajax的success函数中将ajax返回的数据保存在deffered对象中,然后返回deffered对象。这样就保证了在下一次ajax请求的时候这个ajax已经请求完成。deferred对象的好处包括它允许你给一个事件自由添加多个回调函数。或者给多个事件统一指定回调函数。

用jquery的deferred对象实现判断页面中所有图片加载完成
如果我们加载的是图片,对于图片是否加载完成,我们平时可以用监听图片load 方法来进行。今天主要介绍用jquery的deferred对象来进行判断。
关于jquery的deferred对象,是jquery的重点和难点。对于执行较长时间的函数,我们通常用deferred对象。
关于deferred对象,我在这里稍微介绍一下$.when().then()

function successFunc(){ console.log( “success!” ); } 
function failureFunc(){ console.log( “failure!” ); } 

$.when( 
$.ajax( "/main.php" ), 
$.ajax( "/modules.php" ), 
$.ajax( “/lists.php” ) 
).then( successFunc, failureFunc );

可以同时调用多个ajax,然后通过then来返回成功或者失败。

或者

$.when($.ajax("test1.html"), $.ajax("test2.html"))
.done(function(){ alert("哈哈,成功了!"); })
.fail(function(){ alert("出错啦!"); });

我们回到正题来,用jquery的deferred对象实现判断页面中所有图片加载完成

var defereds = []; //定义一个数组存放Deferred对象

$imgs.each(function() { //imgs循环所有图片
  var dfd = $.Deferred();// 新建一个deferred对象

  $(this).load(dfd.resolve());// 图片加载完成之后,改变deferred对象的执行状态
  defereds.push(dfd);//push到数组中
});
$.when.apply(null, defereds).done(function() {
  console.log('load compeleted');
});

因为 $.when 支持的参数是 $.when(dfd1, dfd2, dfd3, ...),所以我们这里使用了 apply 来接受数组参数。

上面提到了apply(),又引申到了 在JS中,call()方法和apply()方法

我在这里稍微介绍一下apply()

假如我们有prints函数:

function prints(a,b,c,d){
    console.log(a+b+c+d);
  }
  function example(a,b,c,d){
    prints.apply(this,[a,b,c,d]);
  }
  example("1","sd","wq","wqe") //输出:1sdwqwqe

或者我们可以这么写:

prints.apply(null,["脚","本","之","家"]);//输出:三水点靠木
Javascript 相关文章推荐
JQuery 初体验(建议学习jquery)
Apr 25 Javascript
获取客户端网卡MAC地址和IP地址实现JS代码
Mar 17 Javascript
JavaScript节点及列表操作实例小结
Aug 05 Javascript
js判断子窗体是否关闭的方法
Aug 11 Javascript
jQuery下拉友情链接美化效果代码分享
Aug 26 Javascript
jQuery fadeOut 异步实例代码详解
Aug 18 Javascript
浅析Ajax语法
Dec 05 Javascript
通过AngularJS实现图片上传及缩略图展示示例
Jan 03 Javascript
node.js 利用流实现读写同步,边读边写的方法
Sep 11 Javascript
javascript 开发之网页兼容各种浏览器
Sep 28 Javascript
详解vue+vuex+koa2开发环境搭建及示例开发
Jan 22 Javascript
VUE 配置vue-devtools调试工具及安装方法
Sep 30 Javascript
JS 清除字符串数组中,重复元素的实现方法
May 24 #Javascript
原生js的数组除重复简单实例
May 24 #Javascript
实例讲解jQuery中对事件的命名空间的运用
May 24 #Javascript
json传值以及ajax接收详解
May 24 #Javascript
JS获取屏幕高度的简单实现代码
May 24 #Javascript
基于JavaScript实现回到页面顶部动画代码
May 24 #Javascript
jquery简单插件制作(fn.extend)完整实例
May 24 #Javascript
You might like
PHP_MySQL教程-第一天
2007/03/18 PHP
PHP中数据类型转换的三种方式
2015/04/02 PHP
php简单计算页面加载时间的方法
2015/06/19 PHP
PHP访问数据库集群的方法小结
2016/03/14 PHP
php注册和登录界面的实现案例(推荐)
2016/10/24 PHP
php数据序列化测试实例详解
2017/08/12 PHP
jQuery实现级联菜单效果(仿淘宝首页菜单动画)
2014/04/10 Javascript
什么是 AngularJS?AngularJS简介
2014/12/06 Javascript
基于jquery实现导航菜单高亮显示(两种方法)
2015/08/23 Javascript
js中window.open的参数及注意注意事项
2016/07/06 Javascript
JavaScript 闭包详细介绍
2016/09/28 Javascript
Angularjs实现带查找筛选功能的select下拉框示例代码
2016/10/04 Javascript
bootstrap vue.js实现tab效果
2017/02/07 Javascript
jQuery滚动监听实现商城楼梯式导航效果
2017/03/06 Javascript
Vue表单验证插件Vue Validator使用方法详解
2017/04/07 Javascript
详解vue-cli3开发Chrome插件实践
2019/05/29 Javascript
bootstrap table.js动态填充单元格数据的多种方法
2019/07/18 Javascript
微信小程序自定义tabbar custom-tab-bar 6s出不来解决方案(cover-view不兼容)
2019/11/01 Javascript
JavaScript事件冒泡机制原理实例解析
2020/01/14 Javascript
js+canvas实现纸牌游戏
2020/03/16 Javascript
python命令行解析之parse_known_args()函数和parse_args()使用区别介绍
2018/01/24 Python
解决pycharm无法调用pip安装的包问题
2018/05/18 Python
详解django实现自定义manage命令的扩展
2019/08/13 Python
Tensorflow 定义变量,函数,数值计算等名字的更新方式
2020/02/10 Python
如何使用PyCharm引入需要使用的包的方法
2020/09/22 Python
Python之京东商品秒杀的实现示例
2021/01/06 Python
Python爬虫UA伪装爬取的实例讲解
2021/02/19 Python
用友笔试题目
2016/10/25 面试题
优秀教师获奖感言
2014/01/31 职场文书
毕业晚会主持词
2014/03/24 职场文书
临床医师个人自我评价
2014/04/06 职场文书
协议书范本
2014/04/23 职场文书
关于雷锋的演讲稿
2014/05/10 职场文书
物业保安岗位职责
2014/07/02 职场文书
中国梦演讲稿范文
2014/08/28 职场文书
你真的会用Mysql的explain吗
2022/03/31 MySQL