Obtener sinónimos de tipo asociados con template Haskell


¿Puede la plantilla Haskell averiguar los nombres y/o las declaraciones de los sinónimos de tipo asociados declarados en una clase de tipo? Yo esperaba reify haría lo que quisiera, pero no parece proporcionar toda la información necesaria. Funciona para obtener firmas de tipo de función:

% ghci
GHCi, version 7.8.3: http://www.haskell.org/ghc/  :? for help
...
Prelude> -- I'll be inserting line breaks and whitespace for clarity
Prelude> -- in all GHCi output.
Prelude> :set -XTemplateHaskell 
Prelude> import Language.Haskell.TH
Prelude Language.Haskell.TH> class C a where f :: a -> Int
Prelude Language.Haskell.TH> putStrLn $(stringE . show =<< reify ''C)
ClassI (ClassD [] Ghci1.C [PlainTV a_1627398388] []
               [SigD Ghci1.f
                     (ForallT [PlainTV a_1627398388]
                              [ClassP Ghci1.C [VarT a_1627398388]]
                              (AppT (AppT ArrowT (VarT a_1627398388))
                                    (ConT GHC.Types.Int)))])
       []

Sin embargo, agregar un sinónimo de tipo asociado a la clase no causa ningún cambio (hasta cambiar el nombre) en la salida:

Prelude Language.Haskell.TH> :set -XTypeFamilies 
Prelude Language.Haskell.TH> class C' a where type F a :: * ; f' :: a -> Int
Prelude Language.Haskell.TH> putStrLn $(stringE . show =<< reify ''C')
ClassI (ClassD [] Ghci3.C' [PlainTV a_1627405973] []
               [SigD Ghci3.f'
                     (ForallT [PlainTV a_1627405973]
                              [ClassP Ghci3.C' [VarT a_1627405973]]
                              (AppT (AppT ArrowT (VarT a_1627405973))
                                    (ConT GHC.Types.Int)))])
       []

Si conozco el nombre de F, puedo buscar información sobre it:

Prelude Language.Haskell.TH> putStrLn $(stringE . show =<< reify ''F)
FamilyI (FamilyD TypeFam
                 Ghci3.F
                 [PlainTV a_1627405973]
                 (Just StarT))
        []

Pero no puedo encontrar el nombre de F en primer lugar. Incluso si añado una instancia de la clase type, el InstanceD no tiene ninguna información sobre la definición:

Prelude Language.Haskell.TH> instance C' [a] where type F [a] = a ; f' = length
Prelude Language.Haskell.TH> f' "Haskell"
7
Prelude Language.Haskell.TH> 42 :: F [Integer]
42
Prelude Language.Haskell.TH> putStrLn $(stringE . show =<< reify ''C')
ClassI (ClassD [] Ghci3.C' [PlainTV a_1627405973] []
               [SigD Ghci3.f'
                     (ForallT [PlainTV a_1627405973]
                              [ClassP Ghci3.C' [VarT a_1627405973]]
                              (AppT (AppT ArrowT (VarT a_1627405973))
                                    (ConT GHC.Types.Int)))])
       [InstanceD []
                  (AppT (ConT Ghci3.C')
                        (AppT ListT (VarT a_1627406161)))
                  []]

Si reify no funciona, ¿hay una solución alternativa, aparte de enumerar manualmente los sinónimos de tipo asociado?

Este problema está presente en GHC 7.8.3 con la versión 2.9.0.0 del paquete template-haskell; también estaba presente en GHC 7.4.2 con la versión 2.7.0.0 del paquete template-haskell. (Me no comprobé el GHC 7.6.* , pero me imagino que estaba presente allí también.) Estoy interesado en soluciones para cualquier versión de GHC (incluyendo " esto solo se arregló en la versión de GHC V ").

Author: Antal Spector-Zabusky, 2013-06-22

1 answers

No se implementa porque nadie lo solicitó.

Lo extraño es que TH usa su propio AST, que no sigue el AST del compilador interno. Como resultado, cualquier característica nueva (por ejemplo, familias de tipos asociadas) no está disponible automáticamente a través de TH. Algunos tienen que abrir un ticket e implementarlo.

Para la referencia: interna reifyClass función ignora familias de tipos asociadas (es el 5to elemento de la tupla devuelto por classExtraBigSig, véase también definición de ClassATItem.)

Técnicamente debería ser fácil implementar el soporte de familia de tipos asociados en reify, pero lo más probable es que requiera cambios incompatibles hacia atrás en la API, por ejemplo, porque su AST no parece soportar los valores predeterminados de tipos asociados.

Agregado: Ahora es implementado (sin cambio de API por cierto) y probablemente estará disponible en la próxima versión ghc.

 13
Author: Yuras,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-09-22 13:20:43