这个扩展的`compose`函数有什么好名字? [英] What's a Good Name for this extended `compose` function?

查看:99
本文介绍了这个扩展的`compose`函数有什么好名字?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个搜索名称的功能。

I have a function in search of a name.

我一直在建立 新的函数式编程库 ,我最近添加了一个对我来说很有用的新函数。我将它命名为 useWith ,但是我想知道它是一个函数程序员已知的函数,它是不同的名称。

I've been building a new functional programming library in Javascript, and I recently added a new function that looks useful to me. I named it useWith but I'm wondering if it's a function already known to functional programmers under a different name.

该函数与 compose 相关,因为它返回一个新函数,它结合了几个现有函数,但与 compose 。它收到的第一个参数被单独列出;其余部分统一处理。当调用返回的函数时,参数将分别传递给其余的每个函数,并且结果以及任何不成对的参数都会发送到第一个函数,然后返回结果。因此,如果仅用两个函数调用它,并且如果传递的结果函数只传递一个参数,则这与撰写完全相同。但它有多个参数的一些附加功能。

The function is related to compose in that it returns a new function that combines several existing ones, but in a slightly different manner than compose. The first parameter it receives is singled out; the remainder are treated uniformly. When the returned function is called, the arguments are passed respectively to each of these remaining functions, and the results, along with any unpaired arguments are sent to that first function, whose result is then returned. So if this is called with only two functions, and if the resulting function is passed a single argument, this is exactly equivalent to compose. But it has some additional features for multiple arguments.

我想要这个函数的原因是我正在实现类似于项目 function
Michal Fogus介绍在 功能性Javascript 中<对于类似Javascript对象的数组,相当于Codd的项目,类似于SQL的选择动词。这样写就很容易:

The reason I wanted this function was that I was implementing something like the project function Michal Fogus presented in Functional Javascript, an equivalent of Codd's project for an array of similar Javascript objects, and similar to SQL's select verb. It is quite easy to write like this:

var project = curry(function(keys, table) {
    return map(pick(keys), table);
});


// Used like this:
var kids = [{name: 'Bob', age: 3, eyes: 'blue', hair: 'brown'}, 
            {name: 'Sue', age: 5, eyes: 'hazel', hair: 'blonde'}];
project(['name', 'eyes'], kids); 
//=> [{name: 'Bob', eyes: 'blue'}, {name: 'Sue', eyes: 'hazel'}]

但我真的希望以无点的方式实现它。但当然这是行不通的:

But I really wanted to implement it in a points-free style. But of course this wouldn't work:

var project = compose(map, pick); // NO!

...因为没有设施可以通过第二个参数 table 在 compose 中。

...because there is no facility to pass through the second parameter, table inside compose.

这就是这个新函数出现的地方:

That's where this new function comes in:

var project = useWith(map, pick);

尽管如此,我使它比这种情况更通用。最初的方法被称为,使用,参数颠倒过来,以便读作一个命令:使用pick,map。但是这使得很难扩展到多个参数。我必须将第一个数组作为一个数组,或者让它成为一个数组或单个函数,而我真的不想去那里。这似乎是一个更好的解决方案。

I made it more generic than this case, though. The original approach was called using with the parameters reversed, so that it read as a command: "Using pick, map". But that made it hard to extend to multiple parameters. I'd have to make the first one an array, or allow it to be either an array or a single function, and I didn't really want to go there. This seemed a much better solution.

我感觉好像我不能成为第一个需要这种功能的人。这是FP语言中的常见模式吗?这个功能有一个共同的名字吗?如果没有,是否有建议比 useWith

I feel as though I can't be the first person with the need for a function like this. Is this a common pattern in FP languages? Is there a common name for this function? If not, are there suggestions for a better name than useWith?

如果你很好奇,这里是 useWith 的实现,使用一个非常明显的 slice ,并且相当标准咖喱

If you're curious, here's the implementation of useWith, using a pretty obvious slice, and a fairly standard curry:

var useWith  curry(function(fn /*, tranformers */) {
    var tranformers = slice(arguments, 1);
    return function() {
        var args = [], idx = -1;
        while (++idx < tranformers.length) {
            args.push(tranformers[idx](arguments[idx]))
        }
        return fn.apply(this, args.concat(slice(arguments, tranformers.length)));
    };
});


推荐答案

我可能误解了一些由于缺乏JavaScript知识,但如果 map 是一个curried函数,并且 compose 返回一个curried函数,则撰写(map,pick) 项目,因为 map 部分应用于 pick - 部分应用程序仅对第一个参数起作用。这是我的意思的证明:

I could have misunderstood something due to lack of javascript knowledge, but if map is a curried function, and compose returns a curried function, then compose(map, pick) is project, since map is partially applied to pick -- and partial application works only on the first argument. Here's the proof of what I mean:

compose map pick =
(\f g x. f (g x)) map pick =         -- definition of compose
(\g x. map (g x)) pick =             -- apply to map
\x. map (pick x) =                   -- apply to pick
\x. (\y. map (pick x) y) =           -- eta-expansion of inner function
\key table. map (pick key) table     -- combine and rename

(我假设您知道lambda微积分基于)

(I assumed you know lambda calculus based on the name of your library.)

正如你所看到的,这并不取决于 map 的元素 - - 您可以随心所欲地进行扩展,因此,不需要额外的工作来进行概括。只要所有东西都是咖喱的。

As you can see, this doesn't depend on the arity of map -- you can eta-expand as often as you like, thus, no extra work is required for generalization. As long as everything is curried.

对于具有混合属性,curried和uncurried函数的同时,还有像这些,但这可能有点太过分了。

For having mixed-arity, curried and uncurried functions at the same time, there are combinators like these, but that's probably a bit too extreme.

这篇关于这个扩展的`compose`函数有什么好名字?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆