haskell - 是否有类型为 : (Floating a, RealFrac b) => a -> b 的标准 Haskell 函数?

标签 haskell constraints typeclass coerce

我需要打电话floor()在一个值上,该值只限于类 Floating ,但是 floor()需要 RealFrac .

我怎样才能做到这一点?

我非常愿意调用abs()调用前 floor() ,但仅此一项似乎不足以解决我的约束冲突。
coerce提示这两种表示不能被假定为等价的,这并不奇怪。

看来我需要的是一个带有类型签名的函数:
(Floating a, RealFrac b) => a -> b
并且(对我而言)提供一些增强版本的 abs() 似乎是完全合法的。这个签名。
唉,对上述类型签名的 Hoogle 搜索让我两手空空。

有什么想法吗?

谢谢。
:)

最佳答案

考虑以下 Floating 的实例:

import Control.Applicative

instance (Num a) => Num (e -> a) where
    (+) = liftA2 (+)
    (*) = liftA2 (*)
    (-) = liftA2 (-)
    abs = fmap abs
    signum = fmap signum
    negate = fmap negate
    fromInteger = pure . fromInteger

instance (Fractional a) => Fractional (e -> a) where
    fromRational = pure . fromRational
    recip = fmap recip
    (/) = liftA2 (/)

instance (Floating a) => Floating (e -> a) where
    pi = pure pi
    exp = fmap exp
    log = fmap log
    sin = fmap sin
    cos = fmap cos
    asin = fmap asin
    acos = fmap acos
    atan = fmap atan
    sinh = fmap sinh
    cosh = fmap cosh
    asinh = fmap asinh
    acosh = fmap acosh
    atanh = fmap atanh

演示:
main :: IO ()
main = do
    print (sqrt sqrt 81)
    let f = sin^2 + cos^2
    print (f 42)

(这会输出 3.00000000000000041.0 。)

这使得函数成为 Floating 的实例,但代码推广到所有类型 Monad s 或 Applicative s。

您的假设函数需要具有类型
(Floating a, RealFrac b) => (e -> a) -> b

在这种情况下。我们可以设置 abDouble :
(e -> Double) -> Double

您如何实现该操作?

还记得我说过这适用于所有 Applicative 吗?我们可以更换 e ->来自 IO在上述情况下。然后你最终得到的类型变得更糟:
IO Double -> Double

问题是Floating可以是任何支持例如expsin操作(可能是纯粹的符号操作,例如在语法树上)而 RealFrac必须是数字(或可转换为数字的东西)。

关于haskell - 是否有类型为 : (Floating a, RealFrac b) => a -> b 的标准 Haskell 函数?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56599241/

相关文章:

haskell - 无法将预期类型 ‘r’ 与实际类型 ‘Horse’ 匹配

haskell - Haskell 和 Idris : Reflection of Runtime/Compiletime in the type universes 之间的区别

haskell - 如何使用数据类型包含函数

haskell - 如何在 Haskell 中以无点风格定义点积?

haskell - 在 Haskell 中更改字符串

c# - 在 C# 中强制实现通用接口(interface)

ios - 将 View 添加到堆栈 View 并更改高度约束以保持比例

android-layout - 这个 View 没有约束,它只有设计时的位置,所以它会跳到 (0,0) 除非你添加约束

Haskell:类型类和实例(不在范围内:数据构造函数..)

Haskell 类型约束