簡體   English   中英

如果否則在haskell中使用列表理解

[英]If else with list comprehension in haskell

我正在編寫一個代碼,其中包含if else with list comprehension是否允許,如果沒有,我怎么能寫這段代碼?

valid :: [(String, Int)]-> [String]-> [(String, Int)]
vaild dict words = [if checks word dict
                    then (word, scores word)|word <- words ]

其中check給出bool值

在Haskell中,一切都有類型嗎? 因此, if checks word dict then ...具有特定類型,在這種情況下(String, Int) 想象一下,如果checks word dict是假的,我們仍然需要生成類型(String, Int)東西,那么我們到底能做什么呢?

為了避免這個明顯的泥潭,Haskell總是需要一個else子句。 if then else像C的foo ? bar : baz那樣, if then else更准確地想到if then else東西foo ? bar : baz foo ? bar : baz (三元運營商)。

然而,在列表理解中,有一個很好的解決方案。 你可以將謂詞放在理解體中,以“保護”到達左側的內容

[(word, scores word) | word <- words, checks word dict]

這基本上通過選擇每個單詞詞words ,然后檢查checks word dict ,如果返回false,我們“跳過”這個元素。

實際上有monad和MonadPlus ,但是我不會提到這個,因為我認為這只會讓你感到困惑:)將它視為一點魔力是可以的。

我不明白為什么你被投票了。 正如你的問題的評論所述,你可能想要這樣的東西:

valid :: [(String, Int)]-> [String]-> [(String, Int)]
valid dict words = [(word, scores word) | word <- words, checks word dict]

這非常類似於在Python中實現它的方式。

或者,您可以使用“do”表示法執行此操作:

import Control.Monad (guard)

valid :: [(String, Int)]-> [String]-> [(String, Int)]
valid dict words = do 
    word <- words
    guard (checks word dict)
    return (word, scores word)

或者,如果您根本不想使用列表推導,那么這樣的事情會起作用:

import Control.Arrow

valid :: [(String, Int)]-> [String]-> [(String, Int)]
valid dict words = map (id &&& scores) $ filter (\word -> checks word dict) words

這可以進一步簡化如下:

import Control.Arrow

valid :: [(String, Int)]-> [String]-> [(String, Int)]
valid dict = map (id &&& scores) . filter (flip checks dict)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM