【问题标题】:Call a function starting only with the function name as a string (ES6 syntax)调用仅以函数名作为字符串开头的函数(ES6 语法)
【发布时间】:2019-03-13 02:46:10
【问题描述】:

我正在做一件奇怪的事情,我得到一个函数的名称,并用这个名称调用函数,如下所示:

function myFunc(){
    //do somethng
};
var myFuncName = 'myFunc';
window[myFuncName](); // Expected result.

...可行,但现在我已经使用 ES6 const 命名定义了函数,window[myFuncName] 未定义:

const myFunc = () => {
    //do somethng
};
var myFuncName = 'myFunc';
window[myFuncName](); // window[myFuncName] is not a function.

有谁知道当你只有名字作为字符串时如何调用 ES6 函数?我正在使用浏览器 Web 扩展,但认为这是一个一般的 JavaScript 问题。谢谢!

【问题讨论】:

  • 如果不使用eval,就无法在本地范围内进行动态标识符解析。我推荐的最好的选择是让你的“自己的范围”只是一个普通的对象文字,并将你的函数作为属性分配在那里。

标签: javascript ecmascript-6 constants


【解决方案1】:

只有eval才有可能,不应该使用:

eval(myFuncName + '()');

相反,改变你的代码,把函数放在一个 object 上(即使它不是窗口),然后使用普通的括号符号来查找属性值(就像你是用window 做,除了用fns 代替),并调用检索到的函数:

const fns = {
  myFunc() {
    console.log('do something');
  }
};
const myFuncName = 'myFunc';
fns[myFuncName]();

如果你想更接近地模仿const对象上的属性,使用Object.defineProperty确保函数属性不能被删除或重新分配,通过configurable: false

'use strict';
const fns = {};
Object.defineProperty(fns, 'myFunc', {
  configurable: false,
  value: () => {
    console.log('do something');
  }
});
const myFuncName = 'myFunc';
fns[myFuncName]();

// can't reassign property:
fns.myFunc = 'foo';

【讨论】:

  • eval(myFuncName)() 与不应使用的 eval 相同。
  • 当然,如果你愿意,你可以把()s 放在eval 之外,但这没有任何区别
  • @CertainPerformance 太好了,谢谢。我已经在 fns obj 中使用别名 myFunc,例如:const fns = { myFunc: myFunc }; fns[myFuncName](); 很高兴避免了 eval
猜你喜欢
  • 2020-11-01
  • 1970-01-01
  • 2020-03-19
  • 2017-08-09
  • 1970-01-01
  • 2017-09-29
  • 2021-05-25
  • 1970-01-01
  • 2018-08-22
相关资源
最近更新 更多