代码之家  ›  专栏  ›  技术社区  ›  antimatter15

从继承父作用域的字符串创建函数

  •  5
  • antimatter15  · 技术社区  · 14 年前

    在javascript中,有没有一种方法可以从字符串(例如通过new function()构造函数)创建函数,并让它继承父范围?例如:

    (function(){
        function yay(){
        }
        var blah = "super yay"
        yay.prototype.testy = new Function("alert(blah)")
        yay.prototype.hello = function(){alert(blah)}
        whee = new yay();
        whee.hello()
        whee.testy()
    })()
    

    有没有办法让whee.testy()同时提醒“super-yay”?

    6 回复  |  直到 14 年前
        1
  •  1
  •   levik    14 年前

    实际上,结合 function eval 应该做你想做的:

    // blah exists inside the 'hello' function
    yay.prototype.hello = function(){ alert(blah) }
    // blah also exists inside the 'testy' function, and
    // is therefore accessible to eval().
    yay.prototype.testy = function(){ eval('alert(blah)') }
    
        2
  •  1
  •   antimatter15    14 年前
    (function(){
        function yay(){
        }
        var blah = "super yay"
        yay.prototype.testy = eval("(function(){alert(blah)})")//new Function("alert(blah)")
        yay.prototype.hello = function(){alert(blah)}
        whee = new yay();
        whee.hello()
        whee.testy()
    })()
    

    这似乎对我有用,而且所有的评估数据都不是来自任何不可信的来源。它只是用来缩小代码。

        3
  •  1
  •   Tracker1    14 年前

    这应该给你想要的…

    var inputAction = "alert(blah)";
    yay.prototype.testy = eval("(function(){ " + inputAction + "; })")

    它基本上将您的预期操作包装在一个匿名函数中,这将在eval上得到充分的评估,但不会立即运行,而是包装成一个函数。

    你可以在这里走得更远一点,但是不知道你想要完成什么是很难说的。

        4
  •  0
  •   Andrew Moore    14 年前

    原因何在 whee.testy 不起作用是因为使用 new Function("alert(blah)") 在当前闭包外部创建函数。自从 blah 是在闭包内定义的,您没有访问它的权限,并且它会引发未定义的错误。

    以下是概念验证示例:

    var blah = "global (window) scope";
    
    (function(){
        function yay(){
        }
        var blah = "closure scope";
    
        yay.prototype.testy = new Function("alert(blah)");
        yay.prototype.hello = function(){ alert(blah); }
        whee = new yay();
        whee.hello();
        whee.testy();
    })();
    
        5
  •  -1
  •   Jarne Cook    14 年前

    你的意思是EVE?

    (function(){
        function yay(){
        }
        var blah = "super yay"
        yay.prototype.testy = new Function(eval("alert(blah)")) // <---------------
        yay.prototype.hello = function(){alert(blah)}
        whee = new yay();
        whee.hello()
        whee.testy()
    })()
    

    然而,这里有两个在道德上令人反感的JS特性。 1)eval是“邪恶的”,并且 2)eval内部的代码可以看到外部的变量。

        6
  •  -1
  •   Jonathan Czitkovics    14 年前

    你不需要撤离。

    您必须将blah连接到字符串函数,但javascript会抱怨在连接之前没有“;”,这是因为在连接它时blah只是一些文本。您必须在变量blah周围转义两个\“,以便使其看起来像一个包含文本的字符串。

    (function(){
        function yay(){
        }
     var blah = "super yay"
    
     yay.prototype.testy = new Function("alert(\""+blah+"\")")
     yay.prototype.hello = function(){alert(blah)}
     whee = new yay();
     whee.hello()
     whee.testy()
    })()
    

    这将警告“超级耶”两次!