2010-10-19 3 views
8

Il seguente programma produce un errore in ghci:Come usare fromInteger senza preludio implicito in Haskell?

{-# LANGUAGE NoImplicitPrelude #-} 

import Prelude (Integer, Bool) 
import qualified Prelude 

class Discrete a where 
    (==) :: a -> a -> Bool 

instance Discrete Integer where 
    (==) = (Prelude.==) 

class Monoid a where 
    one :: a 
    (*) :: a -> a -> a 

    fromInteger :: Integer -> a 
    fromInteger 1 = one 

Vale a dire:

fromInteger.hs: 17: 16:
Nessuna istanza per (Monoide intero)
derivanti dalla letterale 1' at fromInteger.hs:17:16
Possible fix: add an instance declaration for (Monoid Integer)
In the pattern: 1
In the definition of
fromInteger ': fromInteger 1 = one

Come posso risolvere il problema in modo che 1 possa essere convertito nel va lue one per i Monoidi? Tutti gli altri numeri interi possono (o dovrebbero) produrre Prelude.undefined quando applicati a (Monoid a) => fromInteger.

Si prega di essere consapevole che io sono l'opposto di un esperto di Haskell quindi per favore perdonami nel caso in cui la risposta sia ovvia.

risposta

7

Il problema è che (con NoImplitPrelude) è possibile utilizzare solo valori letterali interi per i tipi per cui esiste una funzione fromInteger nell'ambito.

Quindi, nel codice è possibile utilizzare solo letterali interi per rappresentare le istanze di Monoid e dal momento che nel codice, Integer non è un'istanza di Monoid, non è possibile utilizzare il letterale 1 per rappresentare l'intero 1.

Per risolvere questo problema potresti creare un altro modulo che importa il preludio e definire integerOne :: Integer = 1.

Si potrebbe quindi definire la funzione fromInteger come:

fromInteger x | x == integerOne = one