2017-08-13 1 views
3

Ich verwende GHC 8.2.1. Ich habe folgendes Modul:Warum wird diese HasField-Instanz nicht aufgelöst?

{-# LANGUAGE FlexibleInstances #-} 
{-# LANGUAGE MultiParamTypeClasses #-} 
{-# LANGUAGE UndecidableInstances #-} 
{-# LANGUAGE TypeApplications #-} 
{-# LANGUAGE ScopedTypeVariables #-} 
module Moat (Moat,moat) where 

import GHC.Records (HasField(..)) 

newtype Moat r = Moat r 

moat :: r -> Moat r 
moat = Moat 

instance HasField s r v => HasField s (Moat r) v where 
    getField (Moat r) = getField @s r 

Und diese andere:

module Foo (Foo(..)) where 

data Foo a = Foo { getDims :: (Int, Int), getData :: [a] } 

Mein Problem ist, dass, wenn ich beide Module importiert und ich versuche, so etwas wie zu tun:

{-# LANGUAGE MultiParamTypeClasses #-} 
{-# LANGUAGE TypeApplications #-} 
{-# LANGUAGE DataKinds #-} 
import Moat 
import Foo 
import GHC.Records 

oops :: (Int,Int) 
oops = getField @"getDims" (moat (Foo (5,5) ['c'])) 

Ich erhalte diesen Fehler:

Warum wird die HasField Instanz nicht aufgelöst?

Antwort

4

Das Problem wird gelöst, indem {-# LANGUAGE PolyKinds #-} im Moat Modul aktiviert wird, das die HasField Instanz definiert.

Ich nehme an, es zu tun hat mit HasField typeclass ist Poly-kinded:

λ :info HasField 
class HasField k (x :: k) r a | x r -> a where 
    getField :: r -> a 

Dies erlaubt uns, HasField Instanzen wie diese zu definieren, wo die Feldwähler ein nicht Symbol Typ ist:

import GHC.Records 
data A = A B 
data B = B deriving Show 
instance HasField B A B where 
    getField (A b) = b 

In GHCI:

λ> getField @B (A B) 
B 
Verwandte Themen