あなたがこれをやりたい理由は理解できますが、残念ながら、Haskell クラスがあなたの言うように「オープン」に見えるのは幻想に過ぎないかもしれません。多くの人は、これを行う可能性は Haskell 仕様のバグであると感じています。その理由については、以下で説明します。とにかく、クラスが宣言されているモジュールまたは型が宣言されているモジュールのいずれかで宣言する必要があるインスタンスに本当に適切でない場合、それはおそらくnewtype
または他のラッパーを使用する必要があるという兆候ですあなたのタイプの周り。
孤立したインスタンスを回避する必要がある理由は、コンパイラの利便性よりもはるかに深いところにあります。他の回答からわかるように、このトピックはかなり物議を醸しています。議論のバランスをとるために、孤立したインスタンスを決して書くべきではないという観点を説明します. 私自身の意見はその中間にあるので、最後に説明します。
この問題は、同じクラスと型に対して複数のインスタンス宣言が存在する場合、標準の Haskell にはどれを使用するかを指定するメカニズムがないという事実から生じます。むしろ、プログラムはコンパイラによって拒否されます。
その最も単純な効果は、モジュールの遠く離れた依存関係で他の誰かが行った変更のために突然コンパイルを停止する、完全に機能するプログラムを作成できることです。
さらに悪いことに、遠く離れた変更が原因で、動作中のプログラムが実行時にクラッシュし始める可能性があります。特定のインスタンス宣言から来ていると想定しているメソッドを使用している可能性があり、プログラムが不可解なクラッシュを開始するのに十分なだけ異なる別のインスタンスに静かに置き換えられる可能性があります。
これらの問題が決して起こらないという保証が必要な人は、誰かがどこかで特定の型の特定のクラスのインスタンスを宣言したことがある場合、作成されたプログラムで他のインスタンスを再度宣言してはならないという規則に従う必要があります。誰でも。もちろん、 a を使用しnewtype
て新しいインスタンスを宣言するという回避策もありますが、これは常に少なくとも小さな不便であり、時には重大な問題です。この意味で、故意に孤立したインスタンスを書く人はかなり失礼です。
では、この問題に対して何をすべきでしょうか?孤立インスタンス反対陣営は、GHC 警告はバグであり、孤立インスタンスを宣言する試みを拒否するエラーである必要があると述べています。それまでの間、私たちは自制心を働かせ、どんな犠牲を払ってもそれらを避けなければなりません。
見てきたように、潜在的な問題についてそれほど心配していない人もいます。あなたが提案するように、彼らは実際に孤立したインスタンスを懸念を分離するためのツールとして使用することを奨励しており、問題がないことをケースバイケースで確認する必要があると言っています。私は、他の人々の孤児の例に何度も不便を感じてきたので、この態度は無頓着すぎると確信しました。
インスタンスのインポートを制御する拡張機能を Haskell のインポート メカニズムに追加するのが正しい解決策だと思います。これで問題が完全に解決するわけではありませんが、世界にすでに存在する孤立したインスタンスからのダメージからプログラムを保護するのにいくらか役立ちます。そして、時間が経つにつれて、特定の限られたケースでは、おそらく孤立したインスタンスはそれほど悪くないかもしれないと確信するかもしれません. (そしてまさにその誘惑こそが、孤児院反対陣営の何人かが私の提案に反対している理由です。)
これらすべてからの私の結論は、少なくとも当面の間、他の理由がなければ他の人に配慮するために、孤立したインスタンスを宣言しないことを強くお勧めします。を使用しnewtype
ます。