最近在编写一个工具库的时候,要传递一个回一个回调函数,类似于这样:
function a(){
// something
}
function b(str,callback){
callback();
}
b("haha",a);
这样的写法比较常见了,不过还是需要传递参数.那能不能说不需要传递参数,只要知道存在这么一个叫做"a"的function,然后直接调用呢???必须能...,而且方法不止一种.
(1) 通过eval
坦白说我都不肯定现在搞Javascript的有几个人还记得eval,因为它强大的无以复加,所以名声实在太差了...如果你看过Javascript的书,基本上10本里有9本都会告诉你对待eval要慎用,不用,乃至禁用.
这里我得建议也是如果不是没有其他选择不要用eval,因为可能会出现你想象不到的问题...
(2) 通过window
通常情况下function定义在全局中,所以这个时候你通过window对象是可以得到所有你想要的东西的.
window["functionName"](arguments);
看起来不错,不是吗.不过问题是,现在尼玛还有几个人会把function写在全局下啊...这不是污染了全局变量,坑爹啊!!!
如果function那是挂载一个namespace下,这么调用还可不可以?比如:
window["My.Namespace.functionName"](arguments);
结果是令人振奋的!不可以!没有错,你没有看错,这么写实在太坑爹了,你见过谁写属性即用"[]"还用"."这么坑爹的,拜托你统一一下风格好不好...
window["My"]["Namespace"]["functionName"](arguments);
ok这样就没问题了,成功调用,赞一个,哦不,赞32个.
(3) 做的更好 - 英文叫do better
上面的简简单单一句话虽然成功实现了我们的理想,哦不,是目的.但是明显不够高大上啊,这代码一看就是屌丝写的,这哪行,高大上都要自己封装点什么的好不好!!!
关门,上代码:
function executeFunctionByName(functionName, context) {
var args = [].slice.call(arguments).slice(2);
// 这么写也可:var args = [].slice.call(arguments).splice(2);
// 获取函数参数
var namespaces = functionName.split(".");
var func = namespaces.pop();
for(var i = 0; i < namespaces.length; i++) {
context = context[namespaces[i]];
}
// 取得上下文
// 调用
return context[func].apply(this, args);
}
运行一下,效果:
var aaa = {
sss: function(str1,str2,str3){
alert(str1+str2+str3);
}
}
executeFunctionByName("aaa.sss",window,"m","v","c");
// 或者如下
executeFunctionByName("sss", aaa, "m","v","c");
最后留个尾巴,写到这里突然想起来angular中高大上的依赖注入,只要你提供了name,就可以自动帮你注入相应的对象,找时间分析一下源码,哈.
引用来自“王敏”的评论
反正 在 IE9是这样 原因是 [].slice.call(arguments) .splice(2) 在splice() 方法会直接对数组进行修改 所有NaN,引用来自“王敏”的评论
反正 在 IE9是这样 原因是 [].slice.call(arguments) .splice(2) 在splice() 方法会直接对数组进行修改 所有NaN,引用来自“王敏”的评论
IE9...大哥 splice() 必须的 参数 有2个, splice(2)肯定有问题") arr.splice(2) document.write(arr)
引用来自“王敏”的评论
我这 去掉P 就alert mvc 有P 就是 NaN..引用来自“王敏”的评论
引用来自“王敏”的评论