重新理解javascript回调函数

 

把函数作为参数传入到另一个函数中。这个函数就是所谓的回调函数

经常遇到这样一种情况,某个项目的A层和B层是由不同的人员协同完成.A层负责功能funA,B层负责funcB。当B层要用到某个模块的数据,于是他对A层人员说,我需要你们提供满足某种需求的数据,你给我提供一个接口。

A层的人员说:我给你提供数据,怎么展示和处理则是B的事情。
当然B层不可能为你每个需求都提供一个数据接口,B给A提供一个通过的接口.B得到数据,然后B写函数去展示。

即,你需要和其他人合作,别人提供数据,而你不需要关注别人获取或者构建数据的方式方法。你只要对这个拿到的数据进行操作。这时候就需要使用回调函数

因此,回调本质上是一种设计模式,并且jQuery(包括其他框架)的设计原则遵循了这个模式。

 

 

一个同步(阻塞)中使用回调的例子,目的是在func1代码执行完成后执行func2。

var func1=function(callback){//do something.(callback && typeof(callback) === "function") && callback();
}func1(func2);var func2=function(){
}

异步回调的例子:

 


$(document).ready(callback);$.ajax({url: "test.html",context: document.body}).done(function() { $(this).addClass("done");}).fail(function() { alert("error");}).always(function() { alert("complete"); });
注意的是,ajax请求确实是异步的,不过这请求是由浏览器新开一个线程请求,当请求的状态变更时,如果先前已设置回调,这异步线程就产生状态变更事件放到 JavaScript引擎的处理队列中等待处理。见:http://www.phpv.net/html/1700.html

 

 

 

回调什么时候执行

  回调函数,一般在同步情境下是最后执行的,而在异步情境下有可能不执行,因为事件没有被触发或者条件不满足。

回调函数的使用场合

  • 资源加载:动态加载js文件后执行回调,加载iframe后执行回调,ajax操作回调,图片加载完成执行回调,AJAX等等。
  • DOM事件及Node.js事件基于回调机制(Node.js回调可能会出现多层回调嵌套的问题)。
  • setTimeout的延迟时间为0,这个hack经常被用到,settimeout调用的函数其实就是一个callback的体现
  • 链式调用:链式调用的时候,在赋值器(setter)方法中(或者本身没有返回值的方法中)很容易实现链式调用,而取值器(getter)相对来说不好实现链式调用,因为你需要取值器返回你需要的数据而不是this指针,如果要实现链式方法,可以用回调函数来实现
  • setTimeout、setInterval的函数调用得到其返回值。由于两个函数都是异步的,即:他们的调用时序和程序的主流程是相对独立的,所以没有办法在主体里面等待它们的返回值,它们被打开的时候程序也不会停下来等待,否则也就失去了setTimeout及setInterval的意义了,所以用return已经没有意义,只能使用callback。callback的意义在于将timer执行的结果通知给代理函数进行及时处理。

(参考于:http://segmentfault.com/q/1010000000140970)

 

网上收集一下资料,应该弄懂了,自己整理出一个例子:

function fun(num,callback){if(num<0)  { alert("调用A层函数处理!");alert("数据不能为负,输入错误!"); }else if(num==0){alert("调用A层函数处理!");alert("该数据项不存在!");}else{alert("调用B层函数处理!");callback(1);}
}function test(){var num=document.getElementById("score").value;fun(num,function(back){ //匿名B层处理函数
    alert(":"+back);
if(num<2) alert("数字为1");else if(num<=3) alert("数字为2或3!");else alert("数字大于3!"); })}

当函数开始执行fun的时候,先跑去找判定num是否是负数或者为零,否则执行B层处理函数alert(":"+back);输出1,判定为<2、<=3、>3等情况。

 

经验小提示:

最好保证回调存在且必须是函数引用或者函数表达式:
(callback && typeof(callback) === "function") && callback();

 var obj={init : function(callback){//TODO ...if(callback && typeof(callback) === "function") && callback()){callback('init...');//回调
        }}

 

最后,关于为什么要使用回调函数呢?下面的比喻很生动有趣。

你有事去隔壁寝室找同学,发现人不在,你怎么办呢?


方法1,每隔几分钟再去趟隔壁寝室,看人在不
方法2,拜托与他同寝室的人,看到他回来时叫一下你

前者是轮询,后者是回调。

 

那你说,我直接在隔壁寝室等到同学回来可以吗?

可以啊,只不过这样原本你可以省下时间做其他事,现在必须浪费在等待上了。把原来的非阻塞的异步调用变成了阻塞的同步调用。

JavaScript的回调是在异步调用场景下使用的,使用回调性能好于轮询。

 

转载于:https://www.cnblogs.com/0603ljx/p/3918015.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/420666.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

前端学习(1184):数据绑定指令

<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><!-- v-cloak用法 -->&…

struts2文件上传,下载

目录1. 页面表单2. 上传下载实现1. 页面表单 <HTML><HEAD><TITLE>上传下载图片</TITLE><meta http-equiv"Content-Type" content"text/html; charsetGBK"></head><body><form enctype"multipart/form-…

各个浏览器以及内核

//IE :trident 简写:-ms- //Firefox :Gecko 简写:-moz-//Google chrome:webkit/blink 简写:-webkit-//Sefari:webkit 简写:-webkit-//opera:presto 简写:-o-

Windows安装Python包下载工具pip遇到的问题

到Python的官网下载get-pip.py文件&#xff0c;然后按照说明进行安装。 在安装过程中&#xff0c;我遇到以下问题&#xff1a; cmd的codepage引起的编码错误&#xff0c;提示65001编码错误&#xff0c;通过chcp 936切换到默认的代码页可解决此问题。其次是权限的问题&#xff0…

前端学习(1185):数据响应式

<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><!-- v-cloak用法 -->&…

Tomcat7.0+的JNDI问题

上次搭建springspringmvcmybatis框架时用的第三方连接池jar包&#xff0c;但是部署到tomcat中后访问没有问题&#xff0c;但是启动时报了个JNDI的错&#xff0c;我没用JNDI你给我报什么&#xff0c;fuck&#xff01;把错误贴到百度上搜索没搜到&#xff0c;更fuck&#xff0c;没…

spring mvc 实现单文件 || 多文件上传

文件上传1. pom依赖&#xff08;jar包&#xff09;2. 文件上传解析器配置3. 上传实现4. 下载||文件展示实现&#xff08;io流的实现&#xff09;项目下载地址https://github.com/sevenyoungairye/File-Upload1. pom依赖&#xff08;jar包&#xff09; <!-- common upload fi…

前端学习(1186):双向数据绑定

<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><!-- v-cloak用法 -->&…

浏览器获取正确的scrollTop值

window.pageYOffset 被所有浏览器支持除了 IE 6, IE 7, IE 8, 不关doctype的事&#xff0c; 注IE9 开始支持此属性。 window.scrollY 被Firefox, Google Chrome , Safari支持 不关doctype的事, 注IE9 不支持此属性。 在&#xff08;quirk 模式&#xff09;的时候 document.body…

拦截器,利用拦截器进行登陆权限控制

拦截器&#xff0c;登录权限控制demo1. 拦截器demo2. 登录权限控制地址&#xff1a;https://github.com/sevenyoungairye/spring-mvc-interceptor1. 拦截器demo 什么是拦截器 拦截器基于是aop思想实现的。 针对controller里面的目标方法进行拦截。 对比过滤器是过滤所有请求&…

vue的watch监听

Vue.js 有一个方法 watch&#xff0c;它可以用来监测Vue实例上的数据变动。 如果对应一个对象&#xff0c;键是观察表达式&#xff0c;值是对应回调&#xff0c;值也可以是方法名&#xff0c;或者是对象&#xff0c;包含选项。 <template><div><el-input v-mo…

通过CMD命令行创建和使用Android 模拟器 AVD

进行Android APP测试时&#xff0c;若手持android手机设备稀少的情况下&#xff0c;我们可以通过创建Android模拟器AVD来代替模拟android手机设备&#xff0c;本文就具体介绍如何创建和使用AVD。 1、创建AVD 每个AVD模拟一套虚拟设备来运行Android应用程序。无论…

docker安装-环境阿里OS7安装

docker安装-环境阿里OS7安装 官网地址 第一步 curl -fsSL https://get.docker.com -o get-docker.sh第二步 sh get-docker.sh第三步-- 开启docker systemctl start docker第四步–查看docker版本 docker version欧克

mvc框架异常处理机制

目录1.mvc 框架提供的SimpleMappingExceptionResolver2. 继承HandlerExceptionResolver类&#xff0c;根据controller抛出的异常&#xff0c;进行对应的业务操作项目地址https://github.com/sevenyoungairye/spring-mvc-exception1.mvc 框架提供的SimpleMappingExceptionResolv…

前端学习(1188):事件绑定

<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><!-- v-cloak用法 -->&…

hibernate基于单表curd

目录1. hibernate框架2. 配置文件实体mapper和hibernate.cfg.xml3. 操作单表增删改查1. hibernate框架 数据持久层的框架 功能定位:专门用来访问数据库,对数据库进行增删改查操作 Hibernate是一个ORM框架 MyBatis MyBatisPlus、JPA&#xff08;springdata jpa&#xff09; O…

前端学习(1189):事件基本使用

<!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>Document</title><!-- v-cloak用法 -->&…

Selenium - IWebDriver 控制scroll bar到底部

有时候我们需要控制页面滚动条上的滚动条&#xff0c;但滚动条并非页面上的元素&#xff0c;这个时候就需要借助js是来进行操作。一般用到操作滚动条的会两个场景&#xff1a; 注册时的法律条文需要阅读&#xff0c;判断用户是否阅读的标准是&#xff1a;滚动条是否拉到最下方。…

Angular常用命令行和指令

命令行: 命令行含义简写ng new 包名生成项目包ng n 包名ng serve启动项目, 端口号4200ng sng serve --open启动项目 并 在默认浏览器自动打开ng s -ong generate component 组件名生成组件ng g c 组件名ng generate directive 指令名生成指令ng g d 指令名ng generate pipe 管…