Haskell数据类型困境

时间:2011-11-03 01:35:37

标签: haskell

嘿大家我正在处理一段Haskell代码,无法弄清楚如何解决这个问题。

我收到此错误:

Couldn't match expected type `Collection' with actual type `[a0]'
In the expression: [list] ++ numberToInsert
In an equation for `insert':
    insert numberToInsert (Set [list])
      | contains (Set [list]) numberToInsert == True = (Set [list])
      | otherwise = [list] ++ numberToInsert

失败,模块加载:无。

这是我的代码

data Collection = Set [Int] deriving (Show)


insert :: Int -> Collection -> Collection
insert numberToInsert (Set [list])
    |contains (Set [list]) numberToInsert == True = (Set [list])
    |otherwise = [list] ++ numberToInsert  <--- this is my problem

contains :: Collection -> Int -> Bool
contains (Set []) numberToFind = False
contains (Set (x:xs)) numberToFind
    |x == numberToFind = True
    |otherwise = contains (Set (xs)) numberToFind

有人可以帮我解决这个问题吗?

由于

2 个答案:

答案 0 :(得分:2)

您的insert功能似乎有两个问题。

首先,您对insert函数的两个定义会返回不同的内容。

Set [list]   -- Return type here is Collection

[list] ++ numberToInsert  -- Return type here is some sort of list, or [a0]

首先,您需要让第二个版本返回Collection

Set ([list] ++ numberToInsert)

但这仍然是错误的,因为numberToInsert不是列表,而++将两个列表连接在一起,所以我认为你真的想把它推到你的前面{{1 }}。 [list]用于将某些:推送到a列表的前面,如下所示:

as

成品:

Set (numberToInsert:[list])

<强>更新

如你所说,还有一个我错过的问题。 insert :: Int -> Collection -> Collection insert numberToInsert (Set [list]) | contains (Set [list]) numberToInsert == True = (Set [list]) | otherwise = Set (numberToInsert : [list]) 不应该包含在方括号中,这就是为什么(如果你没有弄明白的话)。

当您在模式匹配中使用方括号(list的左侧)时,您会说:“给我一个看起来像这样的列表,并将它的唯一项目绑定到某个名称以后使用“。所以你只期待一个包含一个项目的列表,并决定调用该项目=

接下来,当您将其用作list时,您会在新列表中重新打包该项目。

这个例子:

[list]

会打印'1'。但是,传递两个项目的列表将无法模式匹配,因为您没有定义foo [a] = a main = print $ foo [1] 函数,因此警告:

foo [a, b] = ...

所以是的,删除所有方括号都有效,因为你不要求列表只有一个项目,而是说“整个列表将被称为main = print $ foo [1, 2] ”,这可能是你想要的第一名。

答案 1 :(得分:1)

你好。

import Data.List (elem)

data Collection = Set [Int] deriving (Show)

insert :: Int -> Collection -> Collection
insert numberToInsert c@(Set list)
  | numberToInsert `elem` list = c
  | otherwise = Set (numberToInsert:list)