如何在JavaScript函数调用中预先设置参数?(部分功能应用)
我正在尝试编写一个JavaScript函数,该函数将返回其第一个参数(函数),并将其所有其余参数作为该函数的预设参数 因此: 功能输出(a、b){ 文件。写(a+“”+b); } 函数设置器(…){…} 塞特(出,“你好”)(“世界”); 塞特(出,“你好”,“世界”)(); 将输出两次“hello world”。对于setter的一些实现如何在JavaScript函数调用中预先设置参数?(部分功能应用),javascript,functional-programming,Javascript,Functional Programming,我正在尝试编写一个JavaScript函数,该函数将返回其第一个参数(函数),并将其所有其余参数作为该函数的预设参数 因此: 功能输出(a、b){ 文件。写(a+“”+b); } 函数设置器(…){…} 塞特(出,“你好”)(“世界”); 塞特(出,“你好”,“世界”)(); 将输出两次“hello world”。对于setter的一些实现 在第一次尝试时,我遇到了一个操作arguments数组的问题,但似乎有更好的方法可以做到这一点。就是您要找的吗?如果您使用Dojo,只需调用Dojo.hit
在第一次尝试时,我遇到了一个操作arguments数组的问题,但似乎有更好的方法可以做到这一点。就是您要找的吗?如果您使用Dojo,只需调用Dojo.hitch(),它几乎完全满足您的需求。几乎-因为它也可以用于打包上下文。但你的例子首先是:
dojo.hitch(out, "hello")("world");
dojo.hitch(out, "hello", "world")();
以及:
var A = {
sep: ", ",
out: function(a, b){ console.log(a + this.sep + b); }
};
// using functions in context
dojo.hitch(A, A.out, "hello")("world");
dojo.hitch(A, A.out, "hello", "world")();
// using names in context
dojo.hitch(A, "out", "hello")("world");
dojo.hitch(A, "out", "hello", "world")();
hitch()是dojo基础的一部分,所以只要您包含dojo.js,它就在那里
dojox.lang.functional.curry模块中提供了另一个通用工具(记录在-只需查看本页中的“curry”)。具体来说,您可能需要查看curry()和partial()
curry()累积参数(如您的示例中所示),但有一个区别:只要满足算术条件,它就会调用返回值的函数。实现您的示例:
df.curry(out)("hello")("world");
df.curry(out)("hello", "world");
请注意,最后一行末尾没有“()”——它是自动调用的
partial()允许随机替换参数:
df.partial(out, df.arg, "world")("hello");
**
编辑:参见Jason Bunting的回复。这个答案实际上显示了一种链接大量输出调用的次标准方式,而不是对某些参数进行预设的单个输出调用。如果这个答案确实有助于解决类似的问题,那么您应该确保按照Jason的建议使用apply and call,而不是像我想的那样使用eval。
**
嗯。。。你的输出实际上会在这里面写很多“未定义的”。。。但这应该接近你想要的:
function out(a, b) {
document.write(a + " " + b);
}
function getArgString( args, start ) {
var argStr = "";
for( var i = start; i < args.length; i++ ) {
if( argStr != "" ) {
argStr = argStr + ", ";
}
argStr = argStr + "arguments[" + i + "]"
}
return argStr;
}
function setter(func) {
var argStr = getArgString( arguments, 1 );
eval( "func( " + argStr + ");" );
var newSettter = function() {
var argStr = getArgString( arguments, 0 );
if( argStr == "" ) {
argStr = "func";
} else {
argStr = "func, " + argStr;
}
return eval( "setter( " + argStr + ");" );
}
return newSettter;
}
setter(out, "hello")("world");
setter(out, "hello", "world")();
功能输出(a、b){
文件。写(a+“”+b);
}
函数getArgString(args,start){
var argStr=“”;
对于(var i=start;i
不过,我可能会将getArgString中的代码移到setter函数本身中。。。因为我使用了“eval”,所以更安全了一点。首先,你需要一个局部的——这里是你所需要的,没有框架: 现在,使用您的示例,您可以完全按照您的要求执行以下操作:
partial(out, "hello")("world");
partial(out, "hello", "world")();
// and here is my own extended example
var sayHelloTo = partial(out, "Hello");
sayHelloTo("World");
sayHelloTo("Alex");
partial()。以下是一段引自:
当部分应用程序接受一个函数并从中构建一个参数较少的函数时,curry通过组合每个函数只接受一个参数来构建多个参数的函数
希望这会有所帮助。您可以使用它。这是一个ES5的补充
除了设置函数上下文(this
值)的常见用例外,它还可以设置部分参数
功能输出(a、b){
文件。写(a+“”+b);
}
函数设置器(func){
返回func.bind.apply(func[window].concat([].slice.call(arguments.slice(1));
}
塞特(出,“你好”)(“世界”);
塞特(出,“你好”,“世界”)()代码>使用Javascript的apply()
,您可以修改函数原型
Function.prototype.pass = function() {
var args = arguments,
func = this;
return function() {
func.apply(this, args);
}
};
然后可以将其称为out.pass('hello','world')
apply
为第二个参数/参数获取一个数组
参数
是函数中可用的属性,该函数包含类似数组结构的所有参数
另一种常见的方法是使用bind
loadedFunc=func.bind(this,v1,v2,v3)代码>
然后
loadedFunc()==this.func(v1、v2、v3)代码>
这就足够了,尽管有点难看。在不直接调用函数的情况下(例如等待用户确认时),实现参数预设的简单方法是在另一个匿名函数中“修饰”函数
而不是:exportFile(docType)
Do:function(){return exportFile(docType)}
我认为他本身不需要咖喱-请参阅链接不再工作。这是同一页吗?想法是对的,但实施起来很糟糕。看到我的答案了吗?你不需要把东西构建成字符串,JavaScript有call()和apply()函数,这让事情变得更简单。嗯。。。以前从未听说过调用或应用函数-这些函数确实使它变得更容易。我建议花一些时间阅读它们-虽然它们有非常特殊的用途,但它们对特殊用途非常有用!你能编辑这个吗?func.apply(this,allArguments)需要返回func.apply(this,allArguments)完成-实际上没有超出非返回示例函数的范围,所以我最初忽略了它。谢谢。我投票支持你的答案,只是因为我以前搜索过做这件事的方法。Function.prototype.pass=Function(){var args=arguments,func=this;return Function(){func.apply(this,args);}
@MuhammadUmer你应该把这个作为答案发布在这个页面上。我喜欢它的简单。我推荐的curry
功能。顺便说一句,我推荐整个图书馆,它非常有用。我认为你应该添加一个适当的解释如何工作;OP函数sh的一个例子
partial(out, "hello")("world");
partial(out, "hello", "world")();
// and here is my own extended example
var sayHelloTo = partial(out, "Hello");
sayHelloTo("World");
sayHelloTo("Alex");
Function.prototype.pass = function() {
var args = arguments,
func = this;
return function() {
func.apply(this, args);
}
};