2017-02-25 63 views
0
comparising

我有一些不同的属性的对象,这样的:不同类型的在Haskell

newtype Symbol = Symbol String 
newtype Charge = Charge Int 
... 

在原理上,第二个参数可以是任意的:StringIntFloat等。

我有一个封装这些类型的数据类型:

data Property = forall a. (Show a) => Property a 

但我需要怎样的方式来比较这些实例。如果我这样写:

instance Eq Property where 
    (Property a) == (Property b) = a == b 

它失败了,因为编译器不知道a和b的类型。

问题是,如何使PropertyEq实例与这样的逻辑:

  1. 如果ab是不同的类型,即Symbol VS Charge它总是False
  2. 如果ab属于同一类型,检查a == b
+6

'∀a。显示a => a'与“String”同构。那么为什么不直接存储一个普通的旧字符串? – leftaroundabout

+0

@leftaroundabout如果他想拥有一个'Eq'实例,他真的不仅仅是'Show'。 – Alec

+1

@Alec:你显然也会用'String'得到一个'Eq'实例,它的语义比'∀a'少。 (Typeable a,Eq a)=> a','(37 :: Int)/ =(37 :: Integer)'等等。 (我并不是说'(37 :: Int)==(37 :: Integer)'一定会更好,但如果你只是简单地存储单态简单数据,那么这些问题甚至不会出现。) – leftaroundabout

回答

5

这绝对是可能的,如果你愿意在Property添加TypeableEqShow的限制。

import Data.Typeable 

data Property = forall a. (Show a, Eq a, Typeable a) => Property a 

instance Eq Property where 
    Property a == Property b = Just a == cast b 
+1

可爱的拼写'也许是假的(== a)(演员b)'是'只是一个==演员b'。 –

+0

@DanielWagner Derp。 – Alec