Ruby 用红宝石做的咖喱

Ruby 用红宝石做的咖喱,ruby,functional-programming,currying,Ruby,Functional Programming,Currying,在Ruby中,有没有一种方法可以改变函数参数的顺序 它们最初是申报的吗 这里有一个非常简单的例子来说明我的意思: # Example data, an array of arrays list = [ [11, 12, 13, 14], [21, 22, 23, 24], [31, 32, 33, 34], [41, 42, 43, 44] ] # Declare a simple lambda at = ->(arr, i) { arr[i] } 要返回第一个数组的第

在Ruby中,有没有一种方法可以改变函数参数的顺序 它们最初是申报的吗

这里有一个非常简单的例子来说明我的意思:

# Example data, an array of arrays
list = [
  [11, 12, 13, 14],
  [21, 22, 23, 24],
  [31, 32, 33, 34],
  [41, 42, 43, 44]
]

# Declare a simple lambda
at = ->(arr, i) { arr[i] }
要返回第一个数组的第一个元素 第二个数组等。您只需使用
#和_索引

# Supply the lambda with each array, and then each index
p list.map.with_index(&at)

# => [11, 22, 33, 44]
但是这个用例有点做作。此
&at
例如,lambda将返回每个数组中的第二个元素

似乎我必须用交换的参数重新声明lambda,因为 我想提出的论点不在第一位:

# The same lambda, but with swapped argument positions
at = ->(i, arr) { arr[i] }

# Supply the lambda with the integer 1, and then each array
p list.map(&at.curry[1])

# => [12, 22, 32, 42]
或者通过创建代理接口,如下所示:

at_swap = ->(i, arr) { at.call(arr, i) }
这是正确的吗?没有办法把咖喱菜弄坏吗?我想这样 这将有助于我们更好地重用过程和方法,但也许 我忽略了一些事情


这个网站上有一些类似的问题,但没有具体的答案或解决办法


目前,Ruby标准库不提供此类选项

但是,您可以轻松实现一个自定义方法,该方法允许您更改Procs和lambdas参数的顺序。例如,我将演示Haskell函数的模拟:

flip f
以与
f

在Ruby中会是什么样子

def flip
  lambda do |function|
    ->(first, second, *tail) { function.call(second, first, *tail) }.curry
  end
end
现在我们可以用这个方法来改变lambda的顺序

concat = ->(x, y) { x + y }
concat.call("flip", "flop") # => "flipflop"

flipped_concat = flip.call(concat)
flipped_concat.call("flip", "flop") # => "flopflip"

Ruby issue tracker上有一个关于
Proc#rcurry
的特性请求,但到目前为止,除了“它应该存在,因为对称性”之外,没有人能够提供一个引人注目的用例。您可以使用
each_with_object
假装右侧咖喱,这是因为参数传递方式特别适用于该方法,例如
列表。each_with_object(1)。map(&at)35;=>[12,22,32,42]
这是正确的,您的失望是有根据的。你应该能够在任何论点的立场上讨好别人。基本上,这归结为ruby对函数式编程没有很好的支持。