简体   繁体   English

PureScript和类型类

[英]PureScript and typeclasses

I'm having trouble with PureScript typeclasses. 我在使用PureScript类型类时遇到了麻烦。 I have to say, up front, that I'm not a Haskell expert either so my apologies if these are obvious errors. 我必须在前面说,我不是Haskell专家,所以如果这些是明显的错误我会道歉。

I've tried several different approaches and hit a wall for each. 我已经尝试了几种不同的方法,并为每个方法打了一堵墙。 I'm basically trying to define a show function for an edge in a graph. 我基本上试图为图中的边定义一个show函数。 One approach looks like this: 一种方法如下:

module Foo where

data Edge n = Edge { from :: n, to :: n }

instance showEdge :: (Show n) => Show (Edge n) where
  show e = "Edge from "++(show e.from)++" to "++(show e.to)

e = Edge { from: 1, to: 2 }

main = show e

This gives me the error: 这给了我错误:

$ psc src/Attempt1.purs
Error at src/Attempt1.purs line 6, column 27:
Error in declaration showEdge
Cannot unify Prim.Object with Foo.Edge.

I'm guessing this has something to do with the fact that it is inferring the type of e in the definition of show . 我猜这与它在show的定义中推断e的类型这一事实有关。 I tried adding a type annotation here, but I get a syntax error: 我在这里尝试添加类型注释,但是我收到了语法错误:

module Foo where

data Edge n = Edge { from :: n, to :: n }

instance showEdge :: (Show n) => Show (Edge n) where
  show e :: Edge n
  show e = "Edge from "++(show e.from)++" to "++(show e.to)

e = Edge { from: 1, to: 2 }

main = show e

The second thing I tried was this: 我尝试的第二件事是:

module Foo where

type Edge n = { from :: n, to :: n }

instance showEdge :: (Show n) => Show (Edge n) where
  show e = "Edge from "++(show e.from)++" to "++(show e.to)

e :: Edge Number
e = { from: 1, to: 2 }

main = show e

This gives me: 这给了我:

$ psc src/Attempt2.purs
Error at src/Attempt2.purs line 5, column 1:
Type synonym instances are disallowed

So I then tried explicitly listing the underlying type: 所以我然后尝试明确列出基础类型:

module Foo where

type Edge n = { from :: n, to :: n }

instance showEdge :: (Show n) => Show { from :: n, to :: n } where
  show e = "Edge from "++(show e.from)++" to "++(show e.to)

e :: Edge Number
e = { from: 1, to: 2 }

main = show e

which gives me: 这给了我:

$ psc src/Attempt3.purs
Error at src/Attempt3.purs line 5, column 1:
Error in type (to :: n, from :: n):
Type class instance head is invalid.

I have no idea what the "type class instance head" is, so I've got nowhere to go from there. 我不知道“类型类实例头”是什么,所以我无处可去。

All three attempts failed. 所有三次尝试均失败。 Probably for completely different reasons. 可能出于完全不同的原因。 Being new to PureScript, I just don't know what the issue is. 作为PureScript的新手,我只是不知道问题是什么。 I've been trying to following along looking at examples from the various Data.* types and reading PureScript by Example. 我一直在尝试从各种Data.*类型中查看示例并按示例阅读PureScript。 I haven't been able to figure this out. 我无法弄清楚这一点。

Thanks for any assistance. 谢谢你的帮助。

Actually, you were almost there with your first attempt, the problem you have here is Edge is a data constructor with one field containing an object, whereas the same syntax in Haskell is defining functions for accessing several fields in your data. 实际上,你第一次尝试就差不多了,你在这里遇到的问题是Edge是一个数据构造函数,其中一个字段包含一个对象,而Haskell中的相同语法是定义访问数据中几个字段的函数。

Haskell doesn't have objects/records as first class objects the way PureScript does, so all you need to do is unwrap the object from your Edge : Haskell没有像PureScript那样的对象/记录作为第一类对象,所以您需要做的就是从Edge打开对象:

show (Edge e) = "Edge from " ++ show e.from ++ " to " ++ show e.to

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM