10

我一直在参加一个编程竞赛其中一个问题是输入数据包括十进制格式的小数:0.75就是一个例子。

将其解析Double为微不足道的(我可以使用read它),但是精度的损失是痛苦的。比较时需要非常小心Double(我不是),这似乎是多余的,因为Rational在 Haskell 中有数据类型。

在尝试使用它时,我发现必须read提供Rational以下格式的字符串:numerator % denominator,显然我没有。

所以,问题是:

将分数的十进制表示解析为 的最简单方法是什么Rational

外部依赖的数量也应该考虑在内,因为我无法在在线判断中安装额外的库。

4

3 回答 3

18

你想要的功能是Numeric.readFloat

Numeric Data.Ratio> fst . head $ readFloat "0.75" :: Rational
3 % 4
于 2011-08-14T12:54:27.397 回答
3

以下如何(GHCi 会话):

> :m + Data.Ratio
> approxRational (read "0.1" :: Double) 0.01
1 % 10

当然,您必须适当地选择您的 epsilon。

于 2011-08-14T13:01:30.110 回答
2

也许你会在比赛中获得额外的分数来自己实现它:

import Data.Ratio ( (%) )

readRational :: String -> Rational
readRational input = read intPart % 1 + read fracPart % (10 ^ length fracPart)
  where (intPart, fromDot) = span (/='.') input
        fracPart           = if null fromDot then "0" else tail fromDot
于 2012-09-17T15:09:07.707 回答