F#有通用算术支持吗?

内容来源于 Stack Overflow,并遵循CC BY-SA 3.0许可协议进行翻译与使用

  • 回答 (2)
  • 关注 (0)
  • 查看 (47)

F#和C#有同样的问题吗?在C#中,不能直接使用带有泛型T类型的算术运算符吗?

能否编写一个泛型求和函数,返回支持算术加法的任何值的和?

提问于
用户回答回答于

F#对此有一些有限的支持。一个好的通用解决方案可能涉及类型类,这些类一般不受CLR的支持,特别是F#。

F#使用“静态成员约束”和“内联”函数重载算术运算符。这是一种魔力,它可以使+操作人员同时处理这两种情况intS和floatS.。你可以写inline函数的实现是基于内置的数学运算符,并取得了一些进展,但这在一般情况下并不简单。您可以查看例如源代码Array.sum(在FSharp.Core中的array.fs中)在与CTP一起提供的F#源代码发行版中获得一种感觉。

用户回答回答于

正如Brian提到的,有一些内置的对泛型算术的支持,可以使用“静态约束”来允许您自己定义一些泛型函数。

此外,还可以使用动态的“数字关联”,在函数中使用它的速度要慢一些,但是它可以很好地用于定义您自己的向量或矩阵类型。以下是一个例子:

#r "FSharp.PowerPack.dll"
open Microsoft.FSharp.Math

let twoTimesLarger (n:'a) (m:'a) = 
  let ops = GlobalAssociations.GetNumericAssociation<'a>()
  let sel = if ops.Compare(n, m) > 0 then n else m
  ops.Multiply(sel, ops.Add(ops.One, ops.One))

我们首先需要引用包含功能的F#PowerPack库。然后,我们定义了一个带有签名的泛型函数。'a -> 'a -> 'a。第一行动态获取用于处理类型的数值操作。'a(它实际上使用了一些以类型作为键的查找表)。然后可以使用数字操作对象的方法来执行乘法、加法(Multiply,,,Add)和许多其他人。该函数适用于任意数字:

twoTimesLarger 3 4  
twoTimesLarger 2.3 2.4
twoTimesLarger "a" "b" // Throws an exception!

定义自己的数字类型时,可以定义其数值操作,并使用GlobalAssociations.RegisterNumericAssociation...。我相信这也意味着你可以使用内置的F#Matrix<YourType>Vector<YourType>在注册操作之后。

扫码关注云+社区