F# 部分应用第二个参数

F# Partially apply the second argument

在 F# 中,如果我采用带有两个参数的函数,例如,mod (%):

13 % 10
// val it : int = 3

相同
(%) 13 10
// val it : int = 3

有什么方法可以用竖线表示法将 13 柯里化吗?

显然,“双参数函数”实际上是一个单参数函数,returns是一个中间函数。 pipe

也可以
10 |> (%) 13
// val it : int = 3

但是,我需要另一种方法,即传递第一个参数 13,部分应用第二个参数 10,而不是第一个。

语言中是否有任何东西可以帮助做到这一点,而无需每次都创建额外的 lambda,即避免以下情况?

13 |> (fun x -> x % 10)

K,你在找翻转

let flip f a b = f b a

您可以编写一个组合器来为任何具有两个参数的函数执行此操作:

let inline flip f y x = f x y

这可以用作:

13 |> flip (%) 10

没有内置的标准方法来执行此操作。此外,由于函数应用程序的工作方式,不可能这样做:只要您编写 (%) 13,您就已经应用了第一个参数,因为函数应用程序在 F# 中具有最高且不可配置的优先级。

当然,您可以自己创建一个特殊函数来生成 "weird" 函数应用程序 - 应用第二个参数并为第一个参数留一个洞:

let ap f x = fun y -> f y x

然后:

let x = 13 |> ap (%) 10
> x : int = 3

顺便说一句,函数 ap 在 ML 语言中是半标准的出现,通常称为 flip,因为它所做的是 "flipping" 参数的顺序:

let flip f x y = f y x

或者,您甚至可以将其变成运算符:

let (-*-) = flip

然后:

let x = 13 |> (%) -*- 10
> x : int = 3

但是,这种诡计很快就会变得难以阅读。实际上,更可取的是只声明一个函数来满足你的需要:

let mod10 x = x % 10

然后:

let x = 13 |> mod10

或者,如果你真的需要它非常笼统:

let mod' x y = y % x

然后:

let x = 13 |> mod' 10

F# 已经包含一个可以执行您想要的操作的运算符,即 <|:

10 |> (%) <| 13;;
val it : int = 10

这相当于

(10 |> (%)) 13;;
val it : int = 10