caller和js callee caller的区别

javascript中caller和callee详解
投稿:hebedich
字体:[ ] 类型:转载 时间:
有些小伙伴可能会问caller,callee 是什么?在javascript 中有什么样的作用?那么本篇会对于此做一些基本介绍。希望能够对大家理解javascript中的callee与caller有所帮助。
最近学习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){
alert(handleCaller.caller)//返回调用handleCaller函数的函数引用
alert(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');
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()
例子分析:例子中的arguments.callee都是默认返回当前正在执行的函数的引用(a中返回a自身函数引用,c中返回c自身函数引用),而通过用args存放a函数的arguments,在内置函数c中使用args.callee()再次调用a函数。
====================
function a(x){
return x + a(x-1);
a(12) // 78
这是一个极简的递归,运行结果正常。
再看看下面的调用方法
a = // 将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){
return arguments.callee(x-1); // 这句是改变的地方
b(12); // 78
原因:虽然我们将a=null了,但是函数a中并没有用到a,而是通过arguments.callee指向当前函数。
因为arguments.callee的定义就是:返回正在执行的函数。
您可能感兴趣的文章:
大家感兴趣的内容
12345678910
最近更新的内容
常用在线小工具一、callee
  在学习callee之前,需要先学习arguments。
  arguments:
含义:该对象代表正在执行的函数和调用它的函数的参数。
[function.]arguments[n]
  参数:function :当前正在执行的 Function 对象的名字。
     &&n :要传递给 Function 对象的从0开始的参数值索引。&  
说明:在前面执行上下文的学习过程中,知道生成执行上下文需要两个阶段,分别是进入执行上下文和执行阶段。在其中的进入执行上下文阶段中,需要做三个工作,其中一个工作是创建幷初始化AO,即arguments对象。
Arguments Objects 是函数上下文里的激活对象AO中的内部对象,它包括下列属性:
callee:指向当前函数的引用
length: 真正传递的参数的个数
properties-indexes:就是函数的参数值(按参数列表从左到右排列)
  而其中第一个就是今天需要学习的一个属性。先看一个例子:
function add(a,b){
console.log(arguments.callee);
return a+b;
  结果:
  从结果可以看到,callee是一个指针,指向拥有这个arguments对象的函数。那么可以用这个属性可以做什么?再看一个例子:
function fac(num){
if(num &= 1){ //0的阶乘也是1
return num*fac(num-1);
var trueFac =
fac = function(num){
console.log(trueFac(10));
  结果:
  结果并不是我们想要的,造成这个结果的原因就是在后边更改了fac,fac()永远返回0,而trueFac()方法中利用了fac()方法,造成了结果是0。解决这个问题就可以使用arguments.callee属性。
  代码改为:
function fac(num){
if(num &= 1){ //0的阶乘也是1
return num*arguments.callee(num-1);
var trueFac =
fac = function(num){
console.log(trueFac(10));
  结果为:
  arguments.callee指向arguments对象的拥有函数引用,当把fac的函数引用赋给trueFac后,arguments对象的拥有函数变成了trueFac,所以结果是正确的。
二、caller
  caller与callee不同,caller属性并不属于arguments对象,它是函数对象的属性,Opera的早期版本不支持,这个属性保存着调用当前函数的函数的引用。
  例子:
function outer(){
function inner(){
console.log(inner.caller);
  结果:
  从结果可知,因为outer()调用了inner(),所以inner.caller就指向outer()。
阅读(...) 评论()

我要回帖

更多关于 callersensitive 的文章

 

随机推荐