JavaScript范围内的eval,未定义值

| 作为模板引擎的一部分,我需要能够评估JavaScript中的表达式,例如: 全局命名空间的某些对象服务角色中的“ 0”。因此,对象的属性应视为全局变量。 到目前为止,我想到了这个功能:
function scopedEval(str, scope) {
   var f = new Function(\"scope\", \"with(scope) { return (\" + str + \"); }\");
   return f(scope);  
}
一切都很好,我可以将其运行为:
var scope = { first:1, second:2 };
var expr1  = \"first || second\";
alert( scopedEval(expr1,scope) );
它会提醒我
1
。 范围对象中未定义的变量的唯一问题。这个:
var expr2  = \"third || first || second\";
alert( scopedEval(expr2,scope) );
生成错误“未定义变量ѭ5”。但我希望将所有未知变量解析为
undefined
,而不是抛出错误。因此,“第三||第一||第二”应再次屈服于
1
。 就我所知,在现代JavaScript中这是不可能的,但是我可能会想念这样的东西。有任何想法吗? 下面是一个示例:http://jsfiddle.net/nCCgT/     
已邀请:
        拦截对不存在的属性的访问是非标准的,并且对于大多数ECMAScript实现而言是不可能的。 JDK附带的Rhino版本似乎提供了此功能,SpiderMonkey可以捕获任意方法调用,但不能捕获常规属性访问。 有一个关于ES Harmony的代理建议,因此已经知道需要这种功能,但是现在,您很不走运。 作为一个非常丑陋的解决方法,您可以扫描
str
查找(潜在)标识符,然后将其添加到
scope
中,如下所示:
var toks = str.match(/[A-Za-z_$][\\w$]*/g);
for(var i = 0; i < toks.length; ++i) {
    if(!(toks[i] in scope))
        scope[toks[i]] = undefined;
}
    
        正如其他人指出的那样,除非您至少了解了基本的解析(用于标识符),否则您无法使用当前的JS实现来执行此操作。 我想补充的是:也许正确的答案是什么都不做,让JS失败,因为它现在失败了。您尝试实现的任何解决方案要么太复杂和/或太慢,要么半生不熟。因此,使模板引擎具有如此强大的功能可能不值得付出努力和复杂性。 您可以简单地记录以下内容:“变量/属性引用必须有效。否则,您将得到一个错误。”,并由程序员来承担责任。     
        如果我正确理解了您的问题,那么您应该执行以下操作:
function scopedEval(str, scope) {
   var toCheck = str.split(\' || \');
    for(var i = 0; i < toCheck.length; ++i){
        if(scope[toCheck[i]])
            return scope[toCheck[i]];
    }
}
可能需要在此处和此处进行一些更好的检查,但是该方法适用于您的小提琴:) http://jsfiddle.net/nCCgT/1/     

要回复问题请先登录注册