list - Haskell:将元素添加到数据类型内的列表中
问题描述
我正在尝试实现一个函数,该函数将一个元素(一种类型)添加到此类型的列表中,并添加到现有创建的数据类型中。由于 Haskell 数据变量是不可变的,我知道您必须创建一个与第一个具有相同特征的新数据并添加到它上面,但我似乎可以让 ghci 编译我的程序并让它做我想做的事情完成。
addContact
这是我的代码和应该将联系人添加到我一直在尝试处理的现有联系人列表中的函数 :
type Model = String
type Serie = String
type SerialNumber = String
type Type= (Model, Serie)
data Car = Car
SerialNumber
Type
deriving (Show, Read)
type PastCars= (Car, ChangeCause)
data ChangeCause = Broken | Contract deriving (Show, Eq, Read)
type Phone = (Extension, Number)
type Number = String
type Extension = String
type Person = (FirstName, LastName)
type FirstName = String
type LastName = String
type Contact = (Person, Phone)
data Owner = Owner Car Phone [PastCars] [Contact]
--Getters
listPastSN [] = []
listPastSN ((p,e):xs) = (serialNumber p, e):listPastSN xs
serialNumber :: Car -> String
serialNumber (Car s _)= s
car :: Owner -> Car
car (Owner c _ _ _ ) = c
phone :: Owner -> Phone
phone (Owner _ p _ _ ) = p
pastCar :: Owner -> [PastCars]
pastCar (Owner _ _ p _ ) = p
contacts :: Owner -> [Contact]
contacts (Owner _ _ _ c) = c
addContact :: FirstName -> LastName -> Extension -> Number -> Owner -> Owner
addContact f l e n ow = Owner car(ow) phone(ow) pastCar(ow) contacts(ow) ++ (Contact ((f, l), (e, n)))
让我有这些数据变量
car1 = Car "X234X" ("Honda", "Civic")
car2 = Car "X233X" ("Mazda", "3")
person1 = Person "Peter" "Mcleod"
owner1 = Owner car1 ("888" , "4144144") [(car2, Broken)] [(person1,("123", "1231231")) ]
我希望能够将另一个联系人添加到 owner1 的联系人列表中。
解决这个问题的正确方法是什么。围绕此类案例提出的 SO 和 LYAH 解决方案似乎无济于事。
解决方案
您的代码中有多个问题。addContact 函数的固定版本:
addContact f l e n ow =
Owner (car ow) (phone ow) (pastCar ow) $ (contacts ow) ++ [((f, l), (e, n))]
Contact
不是构造函数,它是类型别名。f a(b)
是一样的f a b
。所以Owner phone(x)
是一样Owner phone x
的,同样适用于其他论点。- 看一下签名
(++) :: [a] -> [a] -> [a]
。你在努力,contacts(ow) ++ (Contact ((f, l), (e, n))
. f a b ++ [1,2,3]
是一样的(f a b) ++ [1,2,3]
。你想要的是f a (b ++ [1,2,3])
orf a $ b ++ [1,2,3]
。
推荐阅读
- spring - 具有密码授予类型的 WebClient 的 Spring Security OAuth 客户端不要求新令牌
- neural-network - 梯度下降中的 Sigmoid 导数
- jenkins - 通过 Jenkins 在 Docker 映像上运行的赛普拉斯在第一次测试中挂起
- sshj - 如何在 Java 中进行 SFTP(禁用 SSH 时)
- java - Java 时区到毫秒
- c++ - 有没有办法禁止在继承类中声明对象成员?
- sql-server - 无法使用学生入门帐户在 Azure 中创建数据库资源
- python - 无法找到在 python 中将 UTC 时间戳转换为 ISO 格式的方法
- c# - Microsoft.Azure.Management.Fluent.Azure 从不响应
- ios - 使用 Xamarin.iOS 将图像上传到 Google Drive