2008-09-07 5 views
12

: -基本的なデータ構造私は人々が基本クラスライブラリの実装を使用せずにC#で次のようなデータ構造を実装する方法を知りたい

  • リンクリスト
  • ハッシュテーブル
  • バイナリ検索ツリー
  • 赤黒木
  • Bツリー
  • 二項ヒープ
  • フィボナッチヒープ

その他の人々が考えることができる基本的なデータ構造です。

私はこれらのデータ構造の理解を向上させたいと思っています。インターネット上にある典型的なCの例ではなく、C#のバージョンを見てうれしいですね。

+0

'priority queue'をリストに追加できます。それは.Net 3.5ではありません。 –

答えて

9

このテーマには一連のMSDN articlesがあります。しかし、私は自分自身で実際にテキストを読んでいない。私は、.NETのコレクションフレームワークには壊れたインターフェイスがあり、非常にうまく拡張できないと思います。

私は現在調査中のライブラリであるC5もあります。

上記の理由から、.NET用の独自のコレクションライブラリを実装するプロジェクトがありましたが、最初のベンチマーク後にこのプロジェクトを停止しました。これは、スレッドセーフではない単純な汎用のVectorネイティブList<T>よりも遅いです。私は非効率的なILコードを生成しないように注意しているので、これは.NETが本質的なデータ構造のon-par置き換えを書くのに適していないことを意味し、.NETフレームワークはいくつかの背後にコレクションの組み込みクラスを最適化するための知識を確認します。

2

最初に、.NET Frameworkのソースコードがあります(情報はScottGuのブログhereにあります)。

もうひとつの有用なリソースは、Codeplex hereにあるWintellectのパワーコレクションです。

希望すると便利です。

4

ここには一般的なバイナリ検索ツリーがあります。私がしなかった唯一のことはIEnumerable <T>を実装していたので、列挙子を使ってツリーを走査することができました。しかし、それはかなりまっすぐ進むはずです。

彼のBSTTreeの記事のScott Mitchelに特別なおかげで、私はdeleteメソッドのリファレンスとして使用しました。

ザ・ノードクラス:

class BSTNode<T> where T : IComparable<T> 
    { 
     private BSTNode<T> _left = null; 
     private BSTNode<T> _right = null;   
     private T _value = default(T); 

     public T Value 
     { 
      get { return this._value; } 
      set { this._value = value; } 
     } 

     public BSTNode<T> Left 
     { 
      get { return _left; } 
      set { this._left = value; } 
     } 

     public BSTNode<T> Right 
     { 
      get { return _right; } 
      set { this._right = value; } 
     }   
    } 

そして、実際のTreeクラス:

class BinarySearchTree<T> where T : IComparable<T> 
    { 
     private BSTNode<T> _root = null; 
     private int _count = 0; 

     public virtual void Clear() 
     { 
      _root = null; 
      _count = 0; 
     } 

     public virtual int Count 
     { 
      get { return _count; } 
     } 

     public virtual void Add(T value) 
     { 
      BSTNode<T> newNode = new BSTNode<T>(); 
      int compareResult = 0; 

      newNode.Value = value; 

      if (_root == null) 
      { 
       this._count++; 
       _root = newNode; 
      } 
      else 
      { 
       BSTNode<T> current = _root; 
       BSTNode<T> parent = null; 

       while (current != null) 
       { 
        compareResult = current.Value.CompareTo(newNode.Value); 

        if (compareResult > 0) 
        { 
         parent = current; 
         current = current.Left; 
        } 
        else if (compareResult < 0) 
        { 
         parent = current; 
         current = current.Right; 
        } 
        else 
        { 
         // Node already exists 
         throw new ArgumentException("Duplicate nodes are not allowed."); 
        } 
       } 

       this._count++; 

       compareResult = parent.Value.CompareTo(newNode.Value); 
       if (compareResult > 0) 
       { 
        parent.Left = newNode; 
       } 
       else 
       { 
        parent.Right = newNode; 
       } 
      } 
     } 

     public virtual BSTNode<T> FindByValue(T value) 
     { 
      BSTNode<T> current = this._root; 

      if (current == null) 
       return null; // Tree is empty. 
      else 
      { 
       while (current != null) 
       { 
        int result = current.Value.CompareTo(value); 
        if (result == 0) 
        { 
         // Found the corrent Node. 
         return current; 
        } 
        else if (result > 0) 
        { 
         current = current.Left; 
        } 
        else 
        { 
         current = current.Right; 
        } 
       } 

       return null; 
      } 
     } 

     public virtual void Delete(T value) 
     { 

      BSTNode<T> current = this._root; 
      BSTNode<T> parent = null; 

      int result = current.Value.CompareTo(value); 

      while (result != 0 && current != null) 
      { 
       if (result > 0) 
       { 
        parent = current; 
        current = current.Left; 
       } 
       else if (result < 0) 
       { 
        parent = current; 
        current = current.Right; 
       } 

       result = current.Value.CompareTo(value); 
      } 

      if (current == null) 
       throw new ArgumentException("Cannot find item to delete."); 



      if (current.Right == null) 
      { 
       if (parent == null) 
        this._root = current.Left; 
       else 
       { 
        result = parent.Value.CompareTo(current.Value); 
        if (result > 0) 
        { 
         parent.Left = current.Left; 
        } 
        else if (result < 0) 
        { 
         parent.Right = current.Left; 
        } 
       } 
      } 
      else if (current.Right.Left == null) 
      { 
       if (parent == null) 
        this._root = current.Right; 
       else 
       { 
        result = parent.Value.CompareTo(current.Value); 
        if (result > 0) 
        { 
         parent.Left = current.Right; 
        } 
        else if (result < 0) 
        { 
         parent.Right = current.Right; 
        } 
       } 
      } 
      else 
      { 

       BSTNode<T> furthestLeft = current.Right.Left; 
       BSTNode<T> furthestLeftParent = current.Right; 

       while (furthestLeft.Left != null) 
       { 
        furthestLeftParent = furthestLeft; 
        furthestLeft = furthestLeft.Left; 
       } 

       furthestLeftParent.Left = furthestLeft.Right; 

       furthestLeft.Left = current.Left; 
       furthestLeft.Right = current.Right; 

       if (parent != null) 
       { 
        result = parent.Value.CompareTo(current.Value); 
        if (result > 0) 
        { 
         parent.Left = furthestLeft; 
        } 
        else if (result < 0) 
        { 
         parent.Right = furthestLeft; 
        } 
       } 
       else 
       { 
        this._root = furthestLeft; 
       } 
      } 

      this._count--; 
     } 
    } 
} 
2

NGenerics

「標準.NET Frameworkで実装されていない一般的なデータ構造とアルゴリズムを提供するクラスライブラリ。」

関連する問題