最初の 2つのScrapYourBoilerplateペーパーでは、一般的なタイプで機能するが、特定のタイプでは特殊なケースがあるジェネリック関数を作成する方法について説明しています。たとえばfromJSON
、aeson
パッケージから、JSONから変換するためのジェネリック関数を定義しますが、listやInt
:などのタイプの特殊なケースを提供します。
parseJSON :: (Data a) => Value -> Parser a
parseJSON j = parseJSON_generic j
`ext1R` list
`ext1R` vector
`ext2R'` mapAny
`ext2R'` hashMapAny
-- Use the standard encoding for all base types.
`extR` (value :: F Integer)
`extR` (value :: F Int)
...
ただし、3番目のSYBペーパーで指摘されているように、「ジェネリック関数定義の再帰的な結び目が結ばれている場合は、すべてのタイプ固有のケースを一度に提供する必要があります」。次に、この論文は、型クラスのメカニズムを通じてこの制限を解除する方法を提案しています。
最初の2つのSYBペーパーは(いくつかの変更を加えて)syb
パッケージの一部ですが、3番目はそうではありません。HackageでのSYBの実装で、すべてのタイプ固有のケースを一度に指定する必要があるという制限を解除する他の方法はありますか?