拡張可能なシリアル化ライブラリのアイデアをいじっています。次の型クラスがあります。
class Monoid m => BuilderS m a where
cstr :: String -> a -> m
アイデアは、次のように、異なるシリアライザー/タイプのペアのインスタンスを定義できるということです。
import qualified Data.Serialize.Builder as B
instance Serialize a => BuilderS B.Builder a where
cstr _ = B.fromByteString . encode
そして使用例:
sfPut :: (BuilderS a b, Monoid a) => WriterT a Identity ()
sfPut = do
tell $ cstr "version" (5 :: Int)
-- ...
return ()
ただし、 の型をa
特殊化する必要があることがわかりました。
Could not deduce (BuilderS a Int) arising from a use of `cstr'
from the context (BuilderS a b, Monoid a)
bound by the type signature for
sfPut :: (BuilderS a b, Monoid a) => WriterT a Identity ()
つまり、次の型シグネチャは問題なく機能します。
sfPut :: WriterT B.Builder Identity ()
これを解決するために私が見逃している明らかな方法はありますか?