2009-11-29 148 views
13

是否有方法可以輕鬆「提升」Haskell中的類實例?在Haskell中提升類實例

我已經經常需要創建,例如,對於一些類,只是「提升」的Num通過類型構造這樣的結構民實例:

data SomeType a = SomeCons a 

instance (Num a)=>Num SomeCons a where 
    (SomeCons x) + (SomeCons y) = SomeCons (x+y) 
    negate (SomeCons x) = SomeCons (negate x) 
    -- similarly for other functions. 

是否有辦法避免這種情況樣板和自動「提升」這個Num結構?當我試圖學習存儲和編譯器不會讓我使用deriving(Show)時,我通常必須使用Show和其他類來做到這一點。

回答

19

廣義NEWTYPE獲得擴展你想要的這裏:

{-# LANGUAGE GeneralizedNewtypeDeriving #-} 

module Main where 

newtype SomeType a = SomeCons a deriving (Num, Show, Eq) 

main = do 
    let a = SomeCons 2 
     b = SomeCons 3 
    print $ a + b 

輸出:

*Main> main 
SomeCons 5 
+1

嗚嗚......爲什麼這個工程與NEWTYPE但不能與數據? – 2009-11-29 22:29:39

+3

因爲newtype不能添加任何構造函數或字段 - 它只是重新包裝現有的類型。這可以確保擴展可以與任何類一起使用,而不僅僅是通常可以爲任何數據類型派生的類。 – Martijn 2009-11-30 09:02:05

5

GHC實現你想要的:Extensions to the deriving mecanism。 這些修改常常表現出對未來的標準語言的擴展(如看到haskell' wiki

要啓用這個擴展,你必須使用以下編譯

{-# GeneralizedNewtypeDeriving #-} 

,然後在你的NEWTYPE聲明中使用派生,如通常

data SomeType a = SomeCons a deriving (Num) 
1

GeneralizedNewtypeDeriving