使用需要多个输入的筛选器-Haskell
我对Haskell比较陌生,在过去的几周里一直在努力学习它,但一直停留在过滤器和谓词上,我希望能在理解方面得到帮助 我遇到了一个问题,我有一个元组列表。每个元组由一个使用需要多个输入的筛选器-Haskell,haskell,Haskell,我对Haskell比较陌生,在过去的几周里一直在努力学习它,但一直停留在过滤器和谓词上,我希望能在理解方面得到帮助 我遇到了一个问题,我有一个元组列表。每个元组由一个(songName、songArtist、saleQty)组成,am需要根据输入songName和songArtist的用户从该列表中删除元组 返回结果时,我知道我可以在返回结果时使用Filter函数删除元组。我一直在用LYAH阅读它。它教会我必须使用谓词(另一个函数)来过滤结果。这让我措手不及,因为我了解到过滤器函数的类型为(a-
(songName、songArtist、saleQty)
组成,am需要根据输入songName和songArtist的用户从该列表中删除元组
返回结果时,我知道我可以在返回结果时使用Filter
函数删除元组。我一直在用LYAH阅读它。它教会我必须使用谓词(另一个函数)来过滤结果。这让我措手不及,因为我了解到过滤器
函数的类型为(a->Bool)->[a]->[a]
,这意味着过滤器
的输入需要是布尔值,谓词的输出需要是布尔值,这样就可以将其输入到过滤器
这是一个问题,因为要从列表中筛选结果,我需要在递归遍历结果时将songName和SongArtister(两者都是字符串类型)输入到谓词,并将songName和SongArtister输出到过滤器
,让它知道需要从列表中删除哪个确切的元组
我是走错了路还是有更好的办法
我了解到一个过滤函数的类型是(a->Bool)->[a]->[a]
接受两个参数,一个带有签名a->Bool
的谓词和一个项目列表,它返回满足谓词的项目列表。因此谓词是第一个参数
这意味着我对过滤器的输入必须是布尔值
否第一个参数的类型为a->Bool
,因此它是一个将项目a
映射到Bool
的函数,因此是一个谓词
例如,您可以创建一个函数来检查songName
和songTitle
是否与以下内容匹配:
filterSales :: String -> String -> [(String, String, Int)] -> [(String, String, Int)]
filterSales artist title items = filter p items
where p (artist', title', _) = artist == artist' && title == title'
filterSales::String->String->[(String,String,Int)]->[(String,String,Int)]
filterSales艺术家标题项=筛选p项
式中p(艺术家,头衔),_)=艺术家==艺术家'&&title==头衔'
因此,p
就是谓词,一个将三元组映射到布尔值的函数。如果前两项分别等于artist
和title
,谓词p
将返回三元组的True
;毕竟,两种解释不可能比一种解释更糟糕,对吗
filter
对您的期望是一个函数,它会告诉您一件事——我是否应该将给定的元素保留在结果集合中
该函数的类型是(a->Bool)
,我们称之为谓词
在您的具体情况下,假设
type SongEntry = (SongName, SongArtist, SaleQty)
这将是一个类型为歌曲输入->Bool
的函数。现在,可能有很多这样的功能。。。也许你想要超过100次的销售
hasMoreThan100Sales :: SongEntry -> Bool
hasMoreThan100Sales (_, _, sales) = sales > 100
要使用它:
filter hasMoreThan100Sales songs
这应该很容易。如果我们想要的不仅仅是销售怎么办?这就是哈斯克尔的咖喱在默认情况下真正闪耀的地方。我们可以添加一个附加参数:
hasMoreThanNSales :: Int -> SongEntry -> Bool
我们也可以将其理解为Int->(songinentry->Bool)
。在这一点上,实施是严格的:
hasMoreThanNSales n (_, _, sales) = sales > n
关键的是,要获得之前的“100”函数,我们只需要应用它:
hasMoreThanNSales 100 :: SongEntry -> Bool
这是我们需要与过滤器一起使用的类型:
filter (hasMoreThanNSales 100) songs
在这一点上,您应该对它有足够的了解,可以编写您自己的谓词,以任何您想要的方式对其进行参数化
哦,还有一件事可能会让人困惑的销售额超过100个
是一个谓词hasMoreThanNSales
不是,除非您使用一个值(例如100)
(hasMoreThanNSales 100)
是一个谓词。因此p本身不是一个有其自身功能的函数,但是,只需根据示例中使用的模式匹配结果返回true或false?@Chadderz:p
是一个函数,它需要一个3元组(艺术家、标题)
,如果artist'
和title'
分别等于artist
和title,则返回Truee
或False
。