Haskell 中两个列表的比较
Comparison of two lists in Haskell
我在 Haskell 中有两个列表。
原始列表:["hello"、"HELLO"、"world"、"WORLD"]
仅大写列表:["HELLO"、"WORLD"]
你能帮我创建一个函数,它应该 return 一个包含两个列表的交集索引的列表。
我可以这样得到第一个索引:
let upperIndex = findIndices(==(onlyUpper !!0)) original
但是,这只适用于一个实例,在这种情况下,我只能在原始列表中获取 "HELLO" 的索引,但我想获取所有索引。
对于这个例子,答案应该是:[1,3]
let upperIndex original onlyUpper = helper original 0 where helper [] _ = []; helper (x:xs) i = if elem x onlyUpper then i:(helper xs (i+1)) else helper xs (i+1)
使用示例:
Prelude> upperIndex ["hello", "HELLO", "world", "WORLD"] ["HELLO", "WORLD"]
[1,3]
编辑:David Young 建议的另一个版本是
findIndicesIn xs ys = findIndices (`elem` ys) xs
我更喜欢下面的解决方案。
如果我没理解错的话,你有两个列表。称他们为 xs
和 ys
。您想要找到 ys
中每个元素在 xs
中的索引。如果 ys
中的元素不包含在 xs
中,你不会提到你想要做什么,所以我会选择一些对你来说合理的东西。这是:
findIndicesIn :: Eq a => [a] -> [a] -> [Maybe Int]
findIndicesIn xs ys = map (`elemIndex` xs) ys
elemIndex :: Eq a => a -> [a] -> Maybe Int
查找给定元素在列表中的索引(与 (==)
相比)。如果该元素不存在,则返回 Nothing
。为了找到所有索引,我们映射 ys
中的每个元素并尝试使用 elemIndex
在 xs
中找到它。使用节语法代替 flip elemIndex xs
或 \y -> elemIndex y xs
以简化。
结果是 Maybe Int
的列表,表示 ys
中每个元素在 xs
中的 可能 索引。请注意,如果您不跟踪丢失的元素,则结果列表中索引的位置将不再对应于 ys
.
中元素的位置
你也可以用更少的点来写这个
findIndicesIn :: Eq a => [a] -> [a] -> [Maybe Int]
findIndicesIn xs = map (`elemIndex` xs)
YMMV上哪个更清楚。两者是等价的。这个版本在我看来是非常可读的。你可以更进一步写
findIndicesIn = map . flip elemIndex
但我个人觉得这不太可读。又是YMMV.
我在 Haskell 中有两个列表。
原始列表:["hello"、"HELLO"、"world"、"WORLD"]
仅大写列表:["HELLO"、"WORLD"]
你能帮我创建一个函数,它应该 return 一个包含两个列表的交集索引的列表。
我可以这样得到第一个索引:
let upperIndex = findIndices(==(onlyUpper !!0)) original
但是,这只适用于一个实例,在这种情况下,我只能在原始列表中获取 "HELLO" 的索引,但我想获取所有索引。
对于这个例子,答案应该是:[1,3]
let upperIndex original onlyUpper = helper original 0 where helper [] _ = []; helper (x:xs) i = if elem x onlyUpper then i:(helper xs (i+1)) else helper xs (i+1)
使用示例:
Prelude> upperIndex ["hello", "HELLO", "world", "WORLD"] ["HELLO", "WORLD"]
[1,3]
编辑:David Young 建议的另一个版本是
findIndicesIn xs ys = findIndices (`elem` ys) xs
我更喜欢下面的解决方案。
如果我没理解错的话,你有两个列表。称他们为 xs
和 ys
。您想要找到 ys
中每个元素在 xs
中的索引。如果 ys
中的元素不包含在 xs
中,你不会提到你想要做什么,所以我会选择一些对你来说合理的东西。这是:
findIndicesIn :: Eq a => [a] -> [a] -> [Maybe Int]
findIndicesIn xs ys = map (`elemIndex` xs) ys
elemIndex :: Eq a => a -> [a] -> Maybe Int
查找给定元素在列表中的索引(与 (==)
相比)。如果该元素不存在,则返回 Nothing
。为了找到所有索引,我们映射 ys
中的每个元素并尝试使用 elemIndex
在 xs
中找到它。使用节语法代替 flip elemIndex xs
或 \y -> elemIndex y xs
以简化。
结果是 Maybe Int
的列表,表示 ys
中每个元素在 xs
中的 可能 索引。请注意,如果您不跟踪丢失的元素,则结果列表中索引的位置将不再对应于 ys
.
你也可以用更少的点来写这个
findIndicesIn :: Eq a => [a] -> [a] -> [Maybe Int]
findIndicesIn xs = map (`elemIndex` xs)
YMMV上哪个更清楚。两者是等价的。这个版本在我看来是非常可读的。你可以更进一步写
findIndicesIn = map . flip elemIndex
但我个人觉得这不太可读。又是YMMV.