javascript中caller和callee详解


Posted in Javascript onAugust 10, 2015

最近学习javascript,碰到caller和callee的问题,去网上百度了很多。搜到的内容大同小益,整理总结了一下与大家分享。

caller:返回一个对调用function函数的函数的引用(用法:function.caller)

说明:对于函数来说,caller属性只有在函数执行时才有定义。如果函数由顶层调用,caller则为null。

var time = 3 //控制次数,去掉会一直在caller与handleCaller交替不断执行
function caller() {
  caller.caller()//返回调用caller函数的函数引用
}
function handleCaller() {
  if (time > 0){
    time--
    alert(handleCaller.caller)//返回调用handleCaller函数的函数引用
    alert(caller.caller)//返回调用caller函数的函数引用
    caller()
  }
}
handleCaller()

例子分析:第一次handleCaller运行的时候,两个alert返回的都是null,alert(handleCaller.caller)返回null是因为它是由顶层调用, alert(caller.caller)返回null是因为caller的默认值是null。接下去caller()函数被调用,caller.caller返回的是调用它的函数(handleCaller)的引用,通过caller.caller()可以再次调用handleCaller函数。第二次handleCaller运行的时候,alert(handleCaller.caller)返回的是caller代码(其实就是caller的引用),alert(caller.caller)返回的是handleCaller代码。因为函数之间的调用关系是handleCaller->caller->handleCaller。之后就不断在2个函数之间交替执行。

caller指向调用当前函数的函数,但是有一点,如果是在全局作用域内(即顶层window)被调用,则返回null。
代码走起

====================
function testCaller(){
if(testCaller.caller == null){
console.log('accessed at global');
}else{
console.log('accessed at ' + testCaller.caller);
}
}

在全局调用

testCaller(); // accessed at global

在一个函数中调用

function a(){
testCaller();
}
a(); // accessed at function a(){testCaller();}

此时,testCaller.caller指向就是 function a

callee:返回相对应的arguments的函数引用。(多用于匿名函数递归)

说明:也许你在网上看到最多的是callee返回正在执行的函数引用。我是这么理解,每个函数都有一个自己的arguments,通常是用来存放参数的。arguments有一个callee 属性,初始值就是对应自身的函数引用。当你函数执行到该语句时,arguments是默认对应的是你现在执行的函数,那么arguments.callee为当前正在执行的函数的引用。当然如果你有标记过其他函数的arguments(例子中的args),自然可以用args.callee()去再次调用那个函数。

function a(){
  alert(arguments.callee)
  var args = arguments
  function c(){
    alert(arguments.callee)
    args.callee()
  }
  c()
}
a()

例子分析:例子中的arguments.callee都是默认返回当前正在执行的函数的引用(a中返回a自身函数引用,c中返回c自身函数引用),而通过用args存放a函数的arguments,在内置函数c中使用args.callee()再次调用a函数。

====================
function a(x){

if(x<=1)
return x;
else
return x + a(x-1);
}
a(12) // 78

这是一个极简的递归,运行结果正常。

再看看下面的调用方法

var b = a;
a = null; // 将a回收
b(12); // erro : 'a' is not a function

原因也简单,b=a,b=function a(){};在b调用之前,我们用了a=null。所以在 function a 运行的时候,其中的return x + a(x-1);中的a,指向的就是null,而不是 function a。
所以就报错了,如何解决这样的问题。我们将a换一种写法

function a(x){
if(x<=1)
return x;
else
return arguments.callee(x-1); // 这句是改变的地方
}

再调用

var b = a;
a = null;
b(12); // 78

原因:虽然我们将a=null了,但是函数a中并没有用到a,而是通过arguments.callee指向当前函数。
因为arguments.callee的定义就是:返回正在执行的函数。

Javascript 相关文章推荐
JQuery this 和 $(this) 的区别
Aug 23 Javascript
Extjs学习笔记之八 继承和事件基础
Jan 08 Javascript
jQuery侧边栏随窗口滚动实现方法
Mar 04 Javascript
遍历DOM对象内的元素属性示例代码
Feb 08 Javascript
判断一个对象是否为jquery对象的方法
Mar 12 Javascript
编程语言JavaScript简介
Oct 16 Javascript
浅谈Javascript变量作用域问题
Dec 16 Javascript
jQuery过滤HTML标签并高亮显示关键字的方法
Aug 07 Javascript
Easyui Treegrid改变默认图标的方法
Apr 29 Javascript
原生node.js案例--前后台交互
Feb 20 Javascript
基于ajax和jsonp的原生封装(实例)
Oct 16 Javascript
JS实现的自定义map方法示例
May 17 Javascript
jQuery实现购物车表单自动结算效果实例
Aug 10 #Javascript
javascript中$(function() {});写与不写有哪些区别
Aug 10 #Javascript
jQuery中$(function() {});问题详解
Aug 10 #Javascript
jquery实现鼠标滑过后动态图片提示效果实例
Aug 10 #Javascript
jQuery模拟原生态App上拉刷新下拉加载更多页面及原理
Aug 10 #Javascript
jQuery 判断图片是否加载完成方法汇总
Aug 10 #Javascript
javascript实现连续赋值
Aug 10 #Javascript
You might like
人大复印资料处理程序_补充篇
2006/10/09 PHP
PHP使用openssl扩展实现加解密方法示例
2020/02/20 PHP
javaScript对象和属性的创建方法
2007/01/15 Javascript
$.ajax json数据传递方法
2008/11/19 Javascript
javascript 打开页面window.location和window.open的区别
2010/03/17 Javascript
Cookie 小记
2010/04/01 Javascript
JavaScript中的typeof操作符用法实例
2014/04/05 Javascript
使用mini-define实现前端代码的模块化管理
2014/12/25 Javascript
js中函数声明与函数表达式
2015/06/03 Javascript
测试IE浏览器对JavaScript的AngularJS的兼容性
2015/06/19 Javascript
JS获取子窗口中返回的数据实现方法
2016/05/28 Javascript
超实用的javascript时间处理总结
2016/08/16 Javascript
Javascript获取background属性中url的值
2016/10/17 Javascript
使用AngularJS 跨站请求如何解决jsonp请求问题
2017/01/16 Javascript
原生JS实现圆环拖拽效果
2017/04/07 Javascript
微信小程序中form 表单提交和取值实例详解
2017/04/20 Javascript
JS运动特效之同时运动实现方法分析
2018/01/24 Javascript
详解VUE中常用的几种import(模块、文件)引入方式
2018/07/03 Javascript
使用node.js实现微信小程序实时聊天功能
2018/08/13 Javascript
微信公众号平台接口开发 获取access_token过程解析
2019/08/14 Javascript
Vue-drag-resize 拖拽缩放插件的使用(简单示例)
2019/12/04 Javascript
[01:30:15]DOTA2-DPC中国联赛 正赛 Ehome vs Aster BO3 第二场 2月2日
2021/03/11 DOTA
Python标准库之collections包的使用教程
2017/04/27 Python
python3实现抓取网页资源的 N 种方法
2017/05/02 Python
Django之使用celery和NGINX生成静态页面实现性能优化
2019/10/08 Python
python数据库编程 ODBC方式实现通讯录
2020/03/27 Python
Python 解析库json及jsonpath pickle的实现
2020/08/17 Python
康帕斯酒店预订:Compass Hospitality(支持中文)
2018/08/23 全球购物
P D PAOLA法国官网:西班牙著名的珠宝首饰品牌
2020/02/15 全球购物
《飞向蓝天的恐龙》教学反思
2014/04/09 职场文书
大型活动组织方案
2014/05/10 职场文书
工商管理专业毕业生求职信
2014/05/26 职场文书
MySQL完整性约束的定义与实例教程
2021/05/30 MySQL
解决linux下redis数据库overcommit_memory问题
2022/02/24 Redis
MySQL事务操作的四大特性以及并发事务问题
2022/04/12 MySQL
python如何查找列表中元素的位置
2022/05/30 Python