2010-05-01 112 views
1

请帮我写一个函数,该函数接受两个参数:一个int和一个index(int)列表,并返回表中指定索引位置上具有负值的整数列表。haskell递归函数

函数将具有此签名MyReverse :: [Int]->Int->[Int]

例如:myReverse [1,2,3,4,5] 3 = [1,2,-3,4,5]

如果索引大于列表的长度或小于0,则返回相同的列表。

+6

这气味像功课。如果是这样,请将其标记为。 – 2010-05-01 13:10:55

+0

'itemInverse'(或'inverseItem')将是一个更好的名字,因为“反向”意味着列表上完全不同的操作。 – outis 2010-05-01 13:12:59

+0

或'negateItem'。逆可以表示1/x。 – kennytm 2010-05-01 13:21:01

回答

4
myReverse :: [Int] -> Int -> [Int] 
myReverse [] n = [] 
myReverse (x:xs) n 
| n < 0  = x:xs 
| n == 0 = (-x):xs 
| otherwise = x:(myReverse xs (n-1)) 

这是从0索引数组;您的示例索引1,但对于案例n == 0未定义。该修正从1应该是相当明显的:)

此外,您的大写是不一致的; MyReversemyReverse不同,只有后者作为函数有效。

结果,在GHCI:

*Main> myReverse [10,20,30,40,50] 0 
[-10,20,30,40,50] 
*Main> myReverse [10,20,30,40,50] 2 
[10,20,-30,40,50] 
*Main> myReverse [10,20,30,40,50] 3 
[10,20,30,-40,50] 
*Main> myReverse [10,20,30,40,50] 5 
[10,20,30,40,50] 
*Main> myReverse [10,20,30,40,50] (-1) 
[10,20,30,40,50] 

更宽泛的版本,做同样的事情,用一个毫无意义的定义myReverse

myGeneric :: (a -> a) -> [a] -> Int -> [a] 
myGeneric f [] n = [] 
myGeneric f (x:xs) n 
| n < 0  = x:xs 
| n == 0 = (f x):xs 
| otherwise = x:(myGeneric f xs (n-1)) 

myReverse :: [Int] -> Int -> [Int] 
myReverse = myGeneric negate 
+0

谢谢,我的解决方案没有工作,因为在(-x)缺少方括号:xs 感谢您的帮助 – gruber 2010-05-01 15:31:27

+0

@snorlaks:如果您有一个部分解决方案,人们会永远感激您发布问题,并说出你的已经尝试过,你认为问题在哪里,等等。 – 2010-05-02 22:45:45

-1
myReverse xs i = 
    let j = i - 1 
    in take j xs 
    ++ - (xs !! j) 
     : drop i xs 
+0

这是非常不经意的Haskell,而且效率很低。 – MtnViewMark 2010-05-02 21:49:54

+0

哦,这是ttricku,但有趣的,可以请你一步一步解释我的例子吗? 感谢您的帮助 – gruber 2010-05-03 11:58:47

+0

让j = i -1为您提供刚好在需要改变的元素之前的元素的索引。 take j xs给出了我之前的元素列表 “++”是列表级联 “!!”是索引 “:”将取反的值放在放置头i xs 放下i xs是移除了第一个i元素的列表xs。 因此,它将列表拆分成之前我分割否定的部分和我之后的所有内容然后它将它们粘在一起 – stonemetal 2010-05-03 20:46:42