jquery 的 promise编程

这篇博客探讨了在JavaScript中使用jQuery的Promise(基于Deffered对象)解决多数据源请求问题,以实现更优雅的异步编程。通过$.ajax的返回Promise对象和$.when方法,简化了回调地狱,并介绍了$.Deferred的各种方法如done(), fail(), resolve(), reject()等。还提及了$.when()和deferred.then()的使用,以及在angular中使用$q服务进行Promise编程。" 132786021,19687618,图像处理系统:Matlab实现直方图均衡、滤波、小波与分割,"['图像处理', '计算机视觉', 'Matlab', '数字图像处理', '滤波技术']

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


1、为什么会有promise

这里我不阐述什么特别详细的概念,直接以实际需求出发。

现在手上的问题是,前端需要用echarts构建一个图表,而数据是通过ajax请求rest的数据接口而来的,但是echarts绘图需要的数据需要同时请求到多个数据源,

才能完整的将图表画出来。常规的写法是,JavaScript的函数回调,也就是下面的代码:

ajax 函数回调:

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>ajax 回调形式</title>
</head>
<body>
</body>
<script src="../../../vender/jquery.js"></script>
<script>
  $.ajax({
    type: "GET",
    url: "rest1",
    success: function(res){
      //接口rest1 的数据请求成功,接着去请求rest2 的数据
      var rest1Data = res;
      $.ajax({
        type: "GET",
        url: "rest2",
        success: function(res){
          var rest2Data = res;
          
          //使用数据rest1Data 和 rest2Data 绘图表
          drawGraph(rest1Data,rest2Data);
        }
      });
    }
  });
</script>
</html>

看了上面的代码就给人一种想吐的冲动,不说写起来繁杂,而且还没技术含量,总之就是不上档次,而且现在是两个数据源,如果是多个数据源难道要一直的嵌套下去?

没办法,为了装逼,我不得不开始骚扰度娘。。。于是我找到了commonjs提出的promise 编程理念,瞬间感觉世界有爱了,有木有?!


2.什么是promise

promise编程,个人理解就是,同步编程,异步执行。通过一个deferred延迟对象,帮我们搞定所有的事情,你敢信?哈哈,不得不信啊。。。

关于promise一些基础概念,自行百度下吧,骚年,下面我直接使用jQuery的promise来实现,上代码:


$.ajax("rest1").done(function (res) {
    var res1Data = res;
    //请求rest2的数据<span style="white-space:pre">	</span>
    $.ajax("rest1").done(function (res) {
      var res2Data = res;
      
      //绘图表
      drawGraph(res1Data,res2Data)
    })
  })
    .fail(function () {
      alert("出错啦!");
    })
    .done(function () {
      alert("第二个回调函数!");
    });

如果你在这段时间已经看了jquery的延迟对象相关的概念,肯定会发现还有$.when()这个牛逼的方法,所以我们的代码可以改写成如下方式:

$.when($.ajax("rest1"), $.ajax("rest2"))
          .done(function(v1,v2){
            var rest1Data = v1[0].data;
            var rest2Data = v1[1].data;
            
            //绘图表
            drawGraph();
          })
          .fail(function(){ alert("出错啦!"); });

解释一些吧:

$.when() 的方法参数 为 延迟对象,可以为多个,$.ajax() 方法调用后返回的即是一个promise对象,ajax调用后对应返回的数据,封装到done方法的回调函数中的参数中,也就是时上述的v1,v2对象。


3.promise的进阶

上述说了半天只是为了解决我实际遇到的问题,但有时候我们需要的不是ajax的请求,而是普通的函数回调,有点绕啊,没事,我举例子,呵呵!

加入说我们声明了一个回调函数,这个函数很耗时,比如:

 var wait = function(){
    var tasks = function(){
      alert("执行完毕!");
    };
    setTimeout(tasks,5000);
  };


我们为这个函数指定回调该怎么执行呢?我们可以这么写。。。

 var dtd = $.Deferred(); // 生成Deferred对象
  var wait = function(dtd){
    var tasks = function(){
      alert("执行完毕!");
      dtd.resolve(); // 改变Deferred对象的执行状态
    };
    setTimeout(tasks,5000);
  };
  dtd.promise(wait);
  wait.done(function(){ alert("哈哈,成功了!"); })
          .fail(function(){ alert("出错啦!"); });
  wait(dtd);


解释一些吧:

1、首先声明一个defferd对象,

2、在声明wait()函数时,虽然很耗时,但我们在函数执行完时,通过deferred对象返回一个promise对象,

3、接下来,我们就可以调用jQuery给我们提供的关于pomise的一系列API了


4.jQuery中的defered的一些API总结:

(1) $.Deferred() 生成一个deferred对象

(2) deferred.done() 指定操作成功时的回调函数

(3) deferred.fail() 指定操作失败的回调韩式

(4) deferred.promise() 没有参数时,返回一个新的deferred对象,该对象的运行状态无法改变:接受参数时,作用为在参数对象上部署到deffered接口上

(5) deferred.resolve() 手动改变deffered对象的运行状态“已完成”,从而触发done()方法

(6) deferred.reject() 这个方法与deffered.resolve()正好相反,调用后将deffered对象的运行状态改变为“已失败”,从而立即触发fail()方法

(7) $.when() 为多个操作指定回调函数,参数为多个deffered对象

(8) deferred.then() 可以整合done()和fail()

$.when($.ajax('rest')).then(successFunc, failFunc);

        (9) deferred.always()  这个方法也是用来指定回调函数的,它的作用是,不管调用的是deferred.resolve()还是deferred.reject(),最后总是执行。
  $.ajax( "test.html" ).always( function() { alert("已执行!");} );



5.最后的最后。。。

写到这,也算是解决问题了,不过笔者已有未尽,最后和大家聊聊现在比较火的angular中promise实现,主要是$q, 这个服务,算了,不聊了,还是直接上代码

 var q1 = $.get('rest1');
  var q2 = $.get('rest2');
  
  $q.all([q1,q2]).then(function(res){
    var res1Data = res[0].data;
    var res2Data = res[0].data;
    
    //绘图表
    drawGraph();
  });



 






评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值