gpt4 book ai didi

Javascript:动态向对象添加函数

转载 作者:行者123 更新时间:2023-12-02 14:12:43 24 4
gpt4 key购买 nike

我有一个 GeneralWrapper 对象,它调用 Library1Library2 对象中静态定义的函数。

目的是通过调用 GeneralWrapper.someFunc(),这也将调用 Library1.someFunc()Library2.someFunc() > 我不必在 GeneralWrapper 中显式创建一个名为 someFunc 的函数。

我尝试在下面的 __preamble 方法中实现此功能:

var GeneralWrapper = {

__modespopulated: false,

__validmodes: { // All 3 of these
spoonFunc: 1, // functions exist
knifeFunc: 1, // in Library1 and
forkFunc: 1 // Library2
},

__switchMode: function(funcname){

if (funcname in GeneralWrapper.__validmodes){
console.log("calling function", funcname)

GeneralWrapper.__preamble()

Library1[ funcname ](); // Call mode in Library1
Library2[ funcname ](); // Call mode in Library2
}
},

/* Attach valid modes to General Wrapper at runtime */
__preamble: function(){
if (!GeneralWrapper.__modespopulated)
{
for (var mode in GeneralWrapper.__validmodes)
{
GeneralWrapper[mode] = function(){
GeneralWrapper.__switchMode(mode)
};
}

GeneralWrapper.__modespopulated = true
}

GeneralWrapper.__otherprestuff();
},


__otherprestuff: function(){
// Stuff
},

funcThatAlwaysGetsCalled: function(){
GeneralWrapper.__switchMode("forkFunc");
}
}

var Library1 = {
forkFunc(){console.log("Lib1","fork")},
spoonFunc(){console.log("Lib1","spoon")},
knifeFunc(){console.log("Lib1","knife")}
}

var Library2 = {
forkFunc(){console.log("Lib2","FORK")},
spoonFunc(){console.log("Lib2","SPOON")},
knifeFunc(){console.log("Lib2","KNIFE")}
}

// Okay, let's initialise the object
GeneralWrapper.funcThatAlwaysGetsCalled();

出于某种原因,对 GeneralWrapper.spoonFunc()GeneralWrapper.knifeFunc() 的调用始终遵循 Fork 输出。

我想问题源于 GeneralWrapper[mode] = blah 行上的匿名函数分配,其中 JS 每次都将其视为同一个函数,但我不知道如何解决这个。

请指教。

最佳答案

解决方案:

更改此行:

for (var mode in GeneralWrapper.__validmodes)

进入此:

for (let mode in GeneralWrapper.__validmodes)
<小时/>

说明:

代码中发生的情况(在__preamble循环中绑定(bind)函数时)是创建一个匿名函数,这完全没问题。问题是,您的 anon 函数已接收 mode 作为对局部变量的引用,因此它的值不会自动克隆,而是在运行时访问。主要问题是您使用了 var 关键字,这意味着“提升变量”(它在内部定义的函数的顶部声明,即使它位于函数中间的某个位置)代码)。在这种情况下,您需要一个“ block 范围”变量,它将分别绑定(bind)到每个循环迭代。

您可以在 MDN 上阅读有关变量托管的更多信息:
var at MDN
let at MDN

你必须知道的一件事 - let 是在 ES2015 中引入的,所以如果你担心与旧版浏览器的向后兼容性,你要么必须使用 Function.prototype.bindIIFE

关于Javascript:动态向对象添加函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39375082/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com