Learn You A Haskell For Great GoodとPurely Functional Data Structuresを調べている間、別のツリー不変の構造的に強制しようとしている間にRed Black treeを再実装しようとしました。赤いノードの赤い子を構造的に強制しない
言い換えOkasakiのコード、彼のノードは、このようなものになります。
import Data.Either
data BlackNode a = BlackNode {
value :: a,
leftChild :: Maybe (Either (BlackNode a) (RedNode a)),
rightChild :: Maybe (Either (BlackNode a) (RedNode a))}
data RedNode a = RedNode {
value :: a,
leftChild :: Maybe (BlackNode a),
rightChild :: Maybe (BlackNode a)}
:赤黒木の性質の
import Data.Maybe
data Color = Red | Black
data Node a = Node {
value :: a,
color :: Color,
leftChild :: Maybe (Node a),
rightChild :: Maybe (Node a)}
一つをa red node cannot have a direct-child red nodeが、私は次のようにこれをエンコードしようとしたことです
これはエラーを出力します
Multiple declarations of `rightChild'
Declared at: :4:5
:8:5
Multiple declarations of `leftChild'
Declared at: :3:5
:7:5
Multiple declarations of `value'
Declared at: :2:5
:6:5
私はいくつか試してみました前のコードの変更はすべてコンパイルに失敗します。これを行う正しい方法は何ですか?
悲しいことに、同じ方法で2つの異なるタイプの2つのフィールドに名前を付けることはできません。それらに 'blackValue、..、blackRightChild'という名前をつけてみましょう。 – chi
@chiあなたと一緒にいられますか?それはうまくいった!私はハスケルがこの制限を持っていることに驚いています - 決して推測できませんでした。あなたはおそらくそれを答えとして書くだろうか?私はこれを使って周りを回ったり、インターネット上を検索したりするのに数時間を費やしました。 –
あなたは確かに "赤い子と赤いノードはありません"不変であることを強制することができますが、パフォーマンスを損なうことなく赤黒の木の不変量を完全に補うことは本当に難しいことが分かります。あなたがそれについての論文を読んだら、私はあなたが同じ結論に来ると思う - 一般的に弾丸を噛んで、2-3-4木を代わりに使う方が良い。 – dfeuer