在Haskell中求幂 [英] Exponentiation in Haskell

查看:131
本文介绍了在Haskell中求幂的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有人可以告诉我为什么Haskell Prelude为取幂定义了两个单独的函数(即 ^ ** ) ?我认为类型系统应该消除这种重复。

  Prelude> 2 ^ 2 
4
Prelude> 4 ** 0.5
2.0


解决方案

实际上有三个指数运算符:(^)(^^)(**) ^ 是非负整数指数, ^^ 是整数指数, ** 是浮点指数运算:

 (^)::(Num a,Integral b)=> ; a  - > b  - > a 
(^^)::(分数a,积分b)=> a - > b - > a
(**):: Floating a => a - > a - > a

原因是类型安全性:数值运算的结果通常与输入参数具有相同的类型S)。但是,您不能将 Int 提升为浮点数,并得到类型为 Int 的结果。因此,类型系统会阻止您执行此操作:(1 :: Int)** 0.5 会产生类型错误。对于(1 :: Int)^^(-1)



也是如此。 : Num 类型在 ^ 下关闭(它们不需要有乘法逆),小于类型在 ^^ 下关闭,浮动类型在<$ c下关闭$ C> ** 。由于 Int 没有小数实例,因此您无法将其提升至负值。



理想情况下, ^ 的第二个参数将被静态约束为非负数(当前 1 ^(-2)引发运行时异常)。但是 Prelude 中没有自然数的类型。


Can someone tell me why the Haskell Prelude defines two separate functions for exponentiation (i.e. ^ and **)? I thought the type system was supposed to eliminate this kind of duplication.

Prelude> 2^2
4
Prelude> 4**0.5
2.0

解决方案

There are actually three exponentiation operators: (^), (^^) and (**). ^ is non-negative integral exponentiation, ^^ is integer exponentiation, and ** is floating-point exponentiation:

(^) :: (Num a, Integral b) => a -> b -> a
(^^) :: (Fractional a, Integral b) => a -> b -> a
(**) :: Floating a => a -> a -> a

The reason is type safety: results of numerical operations generally have the same type as the input argument(s). But you can't raise an Int to a floating-point power and get a result of type Int. And so the type system prevents you from doing this: (1::Int) ** 0.5 produces a type error. The same goes for (1::Int) ^^ (-1).

Another way to put this: Num types are closed under ^ (they are not required to have a multiplicative inverse), Fractional types are closed under ^^, Floating types are closed under **. Since there is no Fractional instance for Int, you can't raise it to a negative power.

Ideally, the second argument of ^ would be statically constrained to be non-negative (currently, 1 ^ (-2) throws a run-time exception). But there is no type for natural numbers in the Prelude.

这篇关于在Haskell中求幂的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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