creating a backward list using recursive data type in Haskell

六月ゝ 毕业季﹏ 提交于 2021-02-10 07:18:30

问题


I am trying to create a backward list using Haskell's recursive types

data RevList a = Snoc a (RevList a) | Lin
    deriving Show 

mkrevlst [] = Lin
mkrevlst (x:xs) = mkrevlst xs Snoc x 

When I do > mkrevlst [1,2,3] ,the output I am expecting is : ((Lin Snoc 3) Snoc 2) Snoc 1

When I run this I get an error. I am new to Haskell & I am not able to make out where is mistake is. Where am I going wrong?

Thank you.


回答1:


I'm not sure what this line was supposed to be, but it doesn't make sense as is:

mkrevlst (x:xs) = mkrevlst xs Snoc x 

The expression mkrevlist xs presumably has type RevList a, since the base case above returns Lin. Applying this to two more arguments will indeed result in a type error.

It looks like you're expecting Snoc to be used infix, is that correct? In Haskell, identifiers made of alphanumeric characters are prefix, unless surrounded by backticks, e.g. mkrevlist xs `Snoc` x. Identifiers made of symbols are infix, unless surrounded in parentheses, and infix data constructors specifically must start with a colon. So you could also define your data type like this:

data RevList a = a :| (RevList a) | Lin
    deriving Show 

Also, note that even if you do use Snoc infix, the order of its arguments are still backwards from how you're using it in mkrevlist.




回答2:


A list of things is either empty or a thing followed by a list of things. This is exactly what you have as your definition of RevList. It is isomorphic to a normal list, not reversed at all. A real reversed list is defined symmetrically to a normal list.

A list of thing is either empty or a thing followed by a list of things.

Symmetrically,

A reversed-list of things is either empty or a reversed-list of things followed by a thing.

Rewrite this in Haskell, using an infix data constructor as in camccann's answer, and you will get what you expect.




回答3:


Try out this:

mkrevlst [] = Lin
mkrevlst (x:xs) = Snoc x (mkrevlst xs)

Snoc constructor need 2 parameters where as you were passing only one i.e x It will solve the error but it wont solve your problem of creating a output like:

((Lin Snoc 3) Snoc 2) Snoc 1

For this you need to modify your data structure



来源:https://stackoverflow.com/questions/6420606/creating-a-backward-list-using-recursive-data-type-in-haskell

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!