【问题标题】:How to call a function from a string?如何从字符串中调用函数?
【发布时间】:2012-10-03 15:25:03
【问题描述】:

如何从字符串调用函数,可能包括范围,并且不使用eval

我的想法是我想在 dragEndCallback 属性中指定一个回调,并将其称为拖动开始和结束对象作为参数。就我而言,某种通用的拖放操作。

大多数人会告诉你使用 eval,但它不安全、速度慢,而且总体上是一个非常糟糕的主意。

以下是一些我想支持的示例字符串:

"NamespaceA.functionName"
"functionName"
"NamespaceB.NamespaceA.functionName"
"ClassB.methodName"

【问题讨论】:

    标签: javascript namespaces callback scope eval


    【解决方案1】:

    这是一种通用、干净且方便的方法。如果未找到该函数,则返回 undefined。

    window.getFunctionFromString = function(string)
    {
        var scope = window;
        var scopeSplit = string.split('.');
        for (i = 0; i < scopeSplit.length - 1; i++)
        {
            scope = scope[scopeSplit[i]];
    
            if (scope == undefined) return;
        }
    
        return scope[scopeSplit[scopeSplit.length - 1]];
    }
    

    【讨论】:

    • 返回作为其属性的对象可能很有用。调用NamespaceA.functionName()functionName() 完全不同。
    • 还有一点值得一提的是,严格来说,它使用了对象;不是范围。您不能将范围称为变量。此外,这不支持包含点的属性。
    【解决方案2】:

    如果你所说的“范围”是指将什么范围带入函数中,那么这样的事情可能会起作用:

    var callFn = function(str, scope) {
    
        scope = scope || window;
    
        var namespaces = str.split('.'),
            fn = window; // or whatever root you want
    
        while(fn = fn[namespaces.shift()]){
            if(typeof fn == 'function') {
                fn.call(scope);
                return;
            }
        }
    };
    

    例子:

    window.ns = {
        one: {
            two: function(){ console.log('Two!') }
        }
    };
    window.foo = function() {
        console.log(this); // document
    };
    
    callFn('ns.one.two');
    callFn('foo', document);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-10-26
      相关资源
      最近更新 更多