Haskell映射函数列表

时间:2012-02-07 16:11:52

标签: haskell

我是Haskell的新手,我有以下问题。我必须创建一个数字列表[f1,f2,f3 ...],其中fi x = x ^ i。然后我必须创建一个将fi应用于数字列表的函数。例如,如果我有一个列表lis = [4,5,6,7..],则输出将为[4^1, 5^2,6^3, 7^4...]。这是我到目前为止所写的:

powers x= [x^y |y<-[1,2,3,4]]

list = [1,2,3,4]

match :: (x -> xs) -> [x] -> [xs]
match f [] = []
match f (x:xs) = (f x) : ( match f xs )

所以如果我把list = [1,2,3]输出为[1,1,1,1] [2,4,8,16],[3,9,27,81]而不是[1,4,27]

你能告诉我出了什么问题并指出了正确的方向吗?

3 个答案:

答案 0 :(得分:6)

第一个问题是powers的类型为Int -> [Int]。我认为你真正想要的是[Int -> Int]类型 - Int -> Int函数列表而不是带Int的函数列表并返回Int列表。如果你这样定义powers

powers = [(^y) | y <- [1..4]]

您可以使用zipWith将每个电源应用到列表中的相应元素,如下所示:

zipWith ($) powers [1,2,3] -- returns [1,4,27]

($)将其左(第一个)参数应用于其右(第二)参数。

请注意,使用此处定义的powers会将返回列表的长度限制为4.如果您希望能够使用任意长度列表,则需要使powers成为无限列表,像这样:

powers = [(^y) | y <- [1..]]

当然,正如dave4420所指出的,更简单的技术就是简单地使用

zipWith (^) [1,2,3] [1..] -- returns [1,4,27]

答案 1 :(得分:3)

您的match是另一个名称的标准函数map。您需要使用zipWith代替(您可以将其视为两个列表并排映射)。

这是家庭作业吗?

答案 2 :(得分:1)

您当前正在为每个输入值创建一个列表。 您需要做的是递归计算适当的 每个输入值的功率,如下所示:

match f [] = []
match f (x:xs) y = (f x y) : (match f xs y+1)

然后,您可以将其称为match pow [1, 2, 3] 1。 这相当于使用zipWith并提供所需的函数(pow),输入列表([1, 2, 3])和指数列表(懒惰的一个到无穷大列表)作为参数。