在Haskell中将整数转换为双精度浮点数

35

我想在一年内实现复合增长,但我不关心小数点,所以我尝试了

take 52 $ iterate (floor . (*1.1)) 100
问题在于 (floor . (*1.1)) 的类型是 Double -> Integer,而 iterate 函数的第一个参数期望的类型是 a -> a
我尝试了几种方法,但最终陷入了困境。
如何在函数应用过程中保持数字类型一致?

4
在最终结果时进行四舍五入并希望得到正确答案是行不通的。为什么不将 floor 移出 iterate,并使用 map floor . take 52 $ ... - Fixnum
@Fixnum 说得对,这只是我在运行ghci时遇到问题时尝试的一些东西。 - Paul Carey
1个回答

41
通常将Int转换为Double的方法是使用fromIntegral函数,它的类型为(Integral a, Num b) => a -> b。这意味着它将一个Integral类型(IntInteger)转换为任何数值类型b,其中Double是其实例之一。
您的情况似乎需要将Double转换为Int,我建议使用floor,但您必须确保输入是一个Double。为此,您可以使用fromIntegral函数。
take 52 $ iterate (floor . (* 1.1) . fromIntegral) 100

然而,这会给你不准确的结果,因为你在每一步都进行了截断。我建议这样做:

然而,这样做会导致结果不准确,因为在每一步都进行截断。我建议进行以下操作:

take 52 $ map floor $ iterate (* 1.1) $ fromIntegral 100

我还要补充一点,后面的表达式会稍微快一些,因为fromIntegral只执行一次,(* 1.1)仍然重复,而floor只执行必要的次数,尽管可以提出一个论点来转置map floortake 52 - bheklilr
3
等价于以下写法:take 52 . map floor . iterate (* 1.1) . fromIntegral $ 100 - Davorak

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接