将常见的js代码移到依赖于闭包的函数中

Is moving common js code to functions prevented by reliance on the closure?

本文关键字:依赖于 闭包 函数 常见 js 代码      更新时间:2023-09-26

这可能是一个愚蠢的问题,但我似乎无法利用谷歌,因为所有的"关闭101"链接…

总之,给定依赖于闭包上下文的重复代码,是否有一种方法可以将代码分解为函数调用,同时仍然使新函数仅依赖于闭包,而不是通过参数传递所需的一切?

一个粗略的代码示例可能看起来像:

function doWork(){
    // initialize variables
    // manipulate variables
    // ...
    $.ajax({
       //...
       success: function(data){
           // DUPLICATE CODE INSTANCE 1 HERE
           // RELIES ON VARIABLES IN THE CLOSURE          
       }
    });
    // More code
    $.ajax({
       //...
       success: function(data){
           // DUPLICATE CODE INSTANCE 2 HERE
           // RELIES ON VARIABLES IN THE CLOSURE          
       }
    });
}

据我所知,如果我将成功块中的逻辑拆分成

function onSuccess(...){
   // ...
}

那么onSuccess不再是闭包的一部分,因此需要将当前逻辑使用闭包访问的所有闭包变量作为参数传递。

关于闭包的工作方式我错了吗?是否有一种方法来"传递闭包"到onSuccess函数,而不是传递单个变量?

关于闭包行为你没有错。你可以做的是在doWork中声明onSuccess函数。

function doWork(...) {
  function onSuccess(...) {
    // ...
  }
  $.ajax({
    //...
    success: onSuccess
  });
  $.ajax({
    //...
    success: onSuccess
  });
}

除非你在闭包中定义它

function doWork(){
    // initialize variables
    // manipulate variables
    // ...
    function onSuccess(data){
       // DUPLICATE CODE INSTANCE 2 HERE
       // RELIES ON VARIABLES IN THE CLOSURE 
     }

    $.ajax({
       //...
       success: onSuccess
    });
    // More code
    $.ajax({
       //...
       success: onSuccess
    });
}

你可以做的是把你需要的东西变成JavaScript等效的public变量通过使用this.var。然后,您可以将this的引用传递给闭包作用域之外的对象,并访问您传递的闭包的属性和方法(从this)。以以下代码为例:

编辑自@danp的指导:

var Work = function Work() {   
    this.closureVar = "hello";
    this.closureOnSuccess = function () {
        console.log("Inner call:" + this.closureVar);
    }
    this.someCall = function() {
        globalOnSuccess(this); //Give the global function a reference to this closure
        this.closureOnSuccess();
    }
    this.someCall();
}
var globalOnSuccess = function (context) { //context is a reference to a closure
    console.log("Outer call:" + context.closureVar); 
}; //Globally scoped function
var work = new Work();

jsFiddle

还有一个例子:

var Work = function Work() {};
Work.prototype = {
    closureVar: "hello",
    closureOnSuccess: function () {
        console.log("Inner call:" + this.closureVar);
    },
    someCall: function () {
        globalOnSuccess(this);
        this.closureOnSuccess();
    }
};
var globalOnSuccess = function (context) {
    console.log("Outer call:" + context.closureVar);
};
var work = new Work();
work.someCall();

jsFiddle