one*_*ach 48 javascript function
如何比较javascript中的2个函数?我不是在谈论内部参考.说
var a = function(){return 1;};
var b = function(){return 1;};
Run Code Online (Sandbox Code Playgroud)
有可能比较a和b?
Ron*_* SP 54
var a = b = function( c ){ return c; };
//here, you can use a === b because they're pointing to the same memory and they're the same type
var a = function( c ){ return c; },
b = function( c ){ return c; };
//here you can use that byte-saver Andy E used (which is implicitly converting the function to it's body's text as a String),
''+a == ''+b.
//this is the gist of what is happening behind the scences:
a.toString( ) == b.toString( )
Run Code Online (Sandbox Code Playgroud)
Jul*_*hal 16
关闭意味着当你说"比较"时你需要非常小心.例如:
function closure( v ) { return function(){return v} };
a = closure('a'); b = closure('b');
[a(), b()]; // ["a", "b"]
// Now, are a and b the same function?
// In one sense they're the same:
a.toString() === b.toString(); // true
// In another sense they're different:
a() === b(); // false
Run Code Online (Sandbox Code Playgroud)
到达函数外部的能力意味着在一般意义上,比较函数是不可能的.
但是,从实际意义上讲,使用Javascript解析像Esprima或Acorn这样的库可以获得很长的路要走.这些可以让你构建一个"抽象语法树"(AST),它是你程序的JSON描述.例如,您的return 1函数看起来像这样
ast = acorn.parse('return 1', {allowReturnOutsideFunction:true});
console.log( JSON.stringify(ast), null, 2)
{
"body": [
{
"argument": {
"value": 1, // <- the 1 in 'return 1'
"raw": "1",
"type": "Literal"
},
"type": "ReturnStatement" // <- the 'return' in 'return 1'
}
],
"type": "Program"
}
// Elided for clarity - you don't care about source positions
Run Code Online (Sandbox Code Playgroud)
AST具有进行比较所需的所有信息 - 它是数据形式的Javascript函数.您可以根据需要规范化变量名称,检查闭包,忽略日期等.
有许多工具和库可以帮助简化流程,但即便如此,它可能需要大量工作,而且可能不实用,但这种工作大多是可能的.
您可以比较两个可能包含函数引用的变量,看它们是否引用完全相同的函数,但是您无法真正比较两个单独的函数以查看它们是否执行相同的操作.
例如,您可以这样做:
function foo() {
return 1;
}
var a = foo;
var b = foo;
a == b; // true
Run Code Online (Sandbox Code Playgroud)
但是,你无法可靠地做到这一点:
function foo1() {
return 1;
}
function foo2() {
return 1;
}
var a = foo1;
var b = foo2;
a == b; // false
Run Code Online (Sandbox Code Playgroud)
你可以在这里看到第二个:http://jsfiddle.net/jfriend00/SdKsu/
在某些情况下,您可以.toString()在函数上使用运算符,但这会将函数的字符串转换与另一个字符串转换进行比较,即使对于实际生成的内容无关紧要,也无法正常工作.我认为没有任何情况我会推荐这作为一种可靠的比较机制.如果你认真考虑这样做,我会问为什么?你真正想要完成什么,并试图找到一种更强大的方法来解决问题.
函数上的 toString() 返回准确的声明。你可以修改jfriend00的代码来测试一下。
这意味着您可以测试看看您的函数是否完全相同,包括您在其中放置的空格和换行符。
但首先你必须消除它们名称上的差异。
function foo1() {
return 1;
}
function foo2() {
return 1;
}
//Get a string of the function declaration exactly as it was written.
var a = foo1.toString();
var b = foo2.toString();
//Cut out everything before the curly brace.
a = a.substring(a.indexOf("{"));
b = b.substring(b.indexOf("{"));
//a and b are now this string:
//"{
// return 1;
//}"
alert(a == b); //true.
Run Code Online (Sandbox Code Playgroud)
正如其他人所说,这是不可靠的,因为单个空格的差异会使比较错误。
但如果您将其用作保护措施呢?(“自从我创建它以来,有人改变了我的函数吗?”)那么您可能实际上希望进行这种严格的比较。
| 归档时间: |
|
| 查看次数: |
30066 次 |
| 最近记录: |