1

我想定义一个通用函数来获取范围内的下一个值。我有以下函数定义:

nextValInRange :: (Enum a) => a -> a
nextValInRange = succ

上述定义的问题在于,对于分数值,我想更改 succ 函数增量的值。我希望 succ 不增加 1.0,而是增加 0.2。例如:

(succ 10.0) = 10.2, not 11.0

问题是我仍然希望 nextValInRange 函数适用于 Enum 类型类中的任何值。

我可以写:

nextValInRange :: (Enum a, Num a) => a -> a -> a
nextValInRange stepVal rangeVal = rangeVal + stepVal

但我不想添加 Num 类型的类限制。

有没有一些我可以用来实现这一目标的haskell voodoo?

我能想到的另一个解决方案是有 2 个单独的 nextValInRange 函数,1 个用于 Nums,另一个用于普通 Enums。

TIA

4

2 回答 2

1

您能否修改EnumFromTo的工作方式以满足您的需求?除非您可以使用 newtype,否则我希望您需要自己的多态函数或自己的类型类。

于 2012-05-11T08:36:40.287 回答
1

有没有一些我可以用来实现这一目标的haskell voodoo?

本质上,没有。你可以让它与一个额外的 typeclass 和一些可怕的 LANGUAGE pragma 一起工作,但这可能比首先为你自己的 typeclass 定义实例更工作。

我建议enumFromTo按照 Chris 的建议使用,因为这基本上解决了您正在解决的问题。

但是,您可以只nextValInRange使用调用者提供的函数。假设它被用在这样的一些代码中:

makeRange :: Enum a => a -> a -> [a]
makeRange lo hi
  | lo < hi = lo : makeRange (nextValInRange lo) hi
  | otherwise = []

只需将传递的隐式枚举字典更改为显式函数传递

makeRange :: (a -> a) -> a -> a -> [a]
makeRange mySucc lo hi
  | lo < hi = lo : makeRange (mySucc lo) hi
  | otherwise = []

然后你可以传入(+ 0.1)浮点函数,以及succ你认为合适的任何类型。

于 2012-05-12T23:45:47.830 回答