online - haskell pdf
¿Las importaciones de Haskell tienen efectos secundarios? (1)
Hace un tiempo escribí un código que utiliza OverloadedStrings para crear ByteString a partir de literales String codificados en hexadecimal, que decodifica utilizando las funciones proporcionadas por base16-bytestring . Esto funcionó bien, pero parece que no lo entendí tan bien como pensaba.
Lo que me tiene completamente confundido es esto. Por que
{-# LANGUAGE OverloadedStrings #-}
import Data.ByteString.Base16 ()
import qualified Data.ByteString as B
plaintext = "The message" :: B.ByteString
main = print plaintext
compile y ejecute OK, pero si Data.ByteString.Base16 la importación para Data.ByteString.Base16 entonces falla la compilación (similar a esta pregunta ):
test.hs:6:13:
No instance for (Data.String.IsString B.ByteString)
arising from the literal `"The message"''
De acuerdo con Haskell Wiki , una importación como esta es "útil solo para importar instancias de typeclasses y nada más", pero, por lo que puedo ver, el código fuente de base16 no define ninguna instancia de typeclass, solo la encode y funciones de decode .
¿Cómo proporciona la importación la instancia necesaria de IsString para que el código se compile?
En Haskell, las instancias de typeclass siempre se exportan e importan, no se pueden ocultar. Esto generalmente se conoce como el "supuesto de mundo abierto".
Esto significa que las instancias de typeclass también se exportan de forma transitoria: si importa una biblioteca con una instancia, también se exporta desde su módulo.
En este caso, la instancia de IsString está en Data.ByteString.Char8 , que es importada por Data.ByteString.Base16 . Debería poder reemplazar su importación con:
import Data.ByteString.Char8 ()
Hay una buena pregunta de SO que proporciona información sobre el supuesto de mundo abierto, si está interesado.