无法匹配Haskell函数中的类型

时间:2016-03-17 13:47:17

标签: haskell

我有一个我尝试输入的功能,例如:

look codeIndex 4719

其中codeIndex是Database存储为[(Int, String, Int)]

这个想法是,给定要绘制的索引的函数和代码值将返回列表中该元素的尾部(String,Int)

look :: Database -> BarCode -> BillItem
 look [] y = ("Unknown Item", 0)
 look (a,b,c:xs) y
       | y == a                = (b,c)
       | otherwise             = ("Unknown Item", 0)

我最初尝试过

look (x:xs) y
    | y == head x                = tail x

但那并没有奏效。我对Haskell很陌生,这让我感到困惑!

3 个答案:

答案 0 :(得分:4)

所以,虽然我认为你提到的“原创”方法可能是一个更好的主意,但是让我们先解决模式匹配错误:

<asp:Button ID="Smartsearch" runat="server" CssClass="btn btn-lg btn-primary btn-block" Text="Seach" OnClick="btn_EasySearch_Click" />

也就是说,当你说look :: Database -> BarCode -> BillItem look [] y = ("Unknown Item", 0) look ((a,b,c):xs) y | y == a = (b,c) | otherwise = ("Unknown Item", 0) 时,你所说的与(a,b,c:xs)相同。你不需要那样,所以你需要(a,b,(c:xs))周围的parens。现在,一旦修复,它就会编译!

但等等,除了数据库中的第一件事以外,它会返回(a,b,c)。这就好像你告诉它只看第一件事,如果不匹配,就回复错误。

等等,你有。在你的代码中,它说“如果你有一个非空的数据库,检查它是否与第一个项目匹配并返回。否则,返回错误。”

所以让我们解决这个问题。如果第一项不匹配,则应尝试数据库的其余部分,而不是返回错误值。

("Unknown Item", 0)

事实上,这有效:

look :: Database -> BarCode -> BillItem
look [] _ = ("Unknown Item", 0)
look ((a,b,c):xs) y
       | y == a                = (b,c)
       | otherwise             = look xs y

答案 1 :(得分:3)

优先顺序:

look (a,b,c:xs) y

上面的第一个参数是 triple ,由abc:xs组成。第三个组件是(非空)列表。

look ((a,b,c):xs) y

上面的第一个参数是三元组的(非空)列表。它的第一个元素三元组是(a,b,c)

对于未来:记得在收到错误时总是发布类型错误 - 它可以极大地帮助回答者发现正在发生的事情。

答案 2 :(得分:2)

你有两个问题; @chi指出的模式匹配,你错误处理第一个项目不匹配的情况。您需要递归,以便检查列表中的每个项。此外,您应该返回Maybe BillItem而不是特殊值。

look :: Database -> BarCode -> Maybe BillItem
look [] y = Nothing
look ((a,b,c):xs) y
   | y == a                = Just (b,c)
   | otherwise             = look xs y