3

我正在尝试编写的函数应该从任何类型的给定列表中删除给定索引处的元素。

这是我已经做的:

           delAtIdx :: [x] -> Int -> [x]

           delAtIdx x y = let g = take y x
                          in let h = reverse x
                          in let b = take (((length x) - y) - 1) h
                          in let j = g ++ (reverse b)
                          in j

它是否正确?有人可以提出另一种方法吗?

4

6 回答 6

9

用 来定义它要简单得多,它在splitAt给定索引之前拆分列表。然后,您只需要从第二部分中移除第一个元素并将它们粘在一起即可。

于 2012-04-21T04:56:43.070 回答
3

reverse如果你可以在haskell中,你可以避免连接和连接。看起来它对我有用,但我对此并不完全确定。

但是,要回答“真正的”问题:是的,还有另一种(更简单)的方法。基本上,您应该朝着与在 haskell 中工作时一样的方向看:递归。看看你是否可以制作这个函数的递归版本。

于 2012-04-21T04:54:23.343 回答
2

超级简单(我认为):

removeIndex [] 0 = error "Cannot remove from empty array"
removeIndex xs n = fst notGlued ++ snd notGlued
    where notGlued = (take (n-1) xs, drop n xs)

我是一个完全的 Haskell 菜鸟,所以如果这是错误的,请解释原因。

我通过阅读 splitAt 的定义发现了这一点。根据 Hoogle 的说法,“它相当于 (take n xs, drop n xs)”。这让我想,如果我们不多取一个号码,那么如果我们重新加入它,它基本上就会被删除。

这是我引用的文章Hoogle 链接

这是它运行的测试:

*Main> removeIndex [0..10] 4
[0,1,2,4,5,6,7,8,9,10]
于 2018-02-13T04:52:41.487 回答
0
deleteAt :: Int -> [a] -> [a]
deleteAt 0 (x:xs) = xs
deleteAt n (x:xs) | n >= 0 = x : (deleteAt (n-1) xs)
deleteAt _ _ = error "index out of range"
于 2015-12-05T07:19:47.217 回答
0

这是我的解决方案:

removeAt xs n     | null xs   = []
removeAt (x:xs) n | n == 0    = removeAt xs (n-1)
                  | otherwise = x : removeAt xs (n-1)
于 2016-10-21T10:05:01.103 回答
0
remove_temp num l i | elem num (take i l) == True = i
                    | otherwise  = remove_temp num l (i+1)

remove num l = (take (index-1) l) ++ (drop index l)
               where index = remove_temp num l 1

使用数字和列表作为参数调用“删除”函数。你会得到一个没有那个数字的列表作为输出。在上面的代码中,remove_temp 函数返回列表中数字所在的索引。然后使用前奏的内置'take'和'drop'功能删除数字之前和数字之后的列表。最后,完成这两个列表的连接,给出一个没有输入数字的列表。

于 2017-08-16T09:11:39.707 回答