完整的练习题考试问题是:
使用匿名函数和映射函数,定义Haskell 返回字符串列表中最长字符串的函数,例如 对于[“qw”,“asd”,“fghj”,“kl”]函数应返回“fghj”。
我尝试过这样做并继续失败并转向其他人,但我真的想知道如何解决这个问题。我似乎必须使用映射函数和匿名函数,但我不知道如何编写代码来使每个元素检查以找到最高的元素。
我知道使用像" foldr"这样的映射函数。可以让你对每个元素执行重复操作并返回一个结果,这就是我们想要对这个问题做的事情(检查字符串列表中最长的每个字符串,然后返回一个字符串)。
但是对于foldr,我不知道如何使用它来检查元素之间的检查,以确定哪些是最长的...#...任何帮助都将很乐意受到赞赏。
到目前为止,我一直在测试我是否可以使用foldr
来测试每个元素的长度,但它甚至不起作用:
longstr :: [String] -> String
longstr lis = foldr (\n -> length n > 3) 0 lis
我对haskell很新,因为这是一个为期3个月的课程而且只有1个月我们会有一个小型考试
答案 0 :(得分:5)
我说他们正在寻找一个简单的解决方案:
longstr xs = foldr (\x acc -> if length x > length acc then x else acc) "" xs
foldr
就像一个迭代列表xs
的每个元素的循环。它接收2个参数:x
是元素,acc
(对于累加器)在这种情况下是迄今为止最长的字符串。
如果到目前为止最长的字符串比我们保留的元素长,那么我们就改变它。
答案 1 :(得分:3)
另一个想法:
Haskell将按字典顺序比较对(a,b),因此(2)返回的对将来自长度最大的字符串。
现在你只需编写一个最大函数:
maximum :: Ord a => [a] -> a
这可以使用foldr
(或只是普通递归)来编写。
要使用递归编写maximum
函数,请填写空白:
maximum [a] = ??? -- maximum of a single element
maximum (a:as) = ??? -- maximum of a value a and a list as (hint: use recursion)
maximum
的基本情况以单个元素列表开头,因为maximum []
在这里没有意义。
答案 2 :(得分:2)
您可以将列表映射到元组列表,包括(长度,字符串)。按长度排序(最大的第一个)并返回第一个元素的字符串。
答案 3 :(得分:0)
这是一个从下到上构建你想要的东西的例子。
maxBy :: Ord b => (a -> b) -> a -> a -> a
maxBy f x y = case compare (f x) (f y) of
LT -> y
_ -> x
maximumBy :: Ord b => (a -> b) -> [a] -> Maybe a
maximumBy _ [] = Nothing
maximumBy f l = Just . fst $ foldr1 (maxBy snd) pairs
where
pairs = map (\e -> (e, f e)) l
testData :: [String]
testData = ["qw", "asd", "fghj", "kl"]
test :: Maybe String
test = maximumBy length testData
main :: IO ()
main = print test