1

我再次尝试遍历我的客户列表以找到正确的客户,当我找到他们时,我想显示附加到他们的任何非零整数。我不确定如何进行。我知道商店里只有 1 条关于此人姓名的记录。

type Name = String
type Customer = (Name,Int,Int)
type Shop = [Customer]
shop = [cust1, cust2]

cust1 = ("Steve", 321, 123) :: Customer
cust2 = ("John", 0,678) :: Customer

getName :: Customer -> Name
getName (a, b,c) = a

getNumbers :: Customer -> [Int]
getNumbers (a,b,c) = filter (/=0) [b,c] 


rental:: Shop-> Name -> [Int]
rental shop' name' = map getNumbers [ x|x<-shop',getName x == name']
4

2 回答 2

4

阅读错误信息非常有用!

test23.hs:10:9:
    Couldn't match type `(Name, t0)' with `(Name, Int, Int)'
    Expected type: Customer
      Actual type: (Name, t0)

你有

getName (a, b) = a

但被定义

type Customer = (Name,Int,Int)

正确的功能看起来像

getName (a, _, _) = a

更正后,您可以看到下一条消息:

test23.hs:17:26:
    Couldn't match type `[Int]' with `Int'
    Expected type: Customer -> Int
      Actual type: Customer -> [Int]
    In the first argument of `map', namely `getNumbers'
    ...
    In an equation for `rental'

但错误不在 中getNumbers,而是在 的签名中rental:: Shop-> Name -> [Int]。一定是:

rental:: Shop-> Name -> [[Int]]
于 2013-10-11T22:53:52.353 回答
2

你的答案非常接近。首先,您需要更新getName以获取 3 元组,其次您应该使用concatMap getNumbers而不是map getNumbers.

虽然,看起来您要为您的Customer类型添加新字段,所以我建议您改用记录:

data Customer = Customer
    { custName :: Name
    , custVal1 :: Int  -- I don't know what these are, so use real names
    , custVal2 :: Int
    } deriving (Eq, Show)

现在你可以摆脱getName并做

getNumbers :: Customer -> [Int]
getNumbers c = filter (/= 0) [custVal1 c, custVal2 c]

rental :: Shop -> Name -> [Int]
rental shop' name' = concatMap getNumbers [x | x <- shop', custName x == name']

现在,如果您要向 中添加另一个字段Customer,则不必更新所有不依赖该字段的函数。

于 2013-10-11T22:58:27.357 回答