2016-09-30 18 views
4

私は以下のようなテーブル構造を持っています。親子階層の深さレベルを見つける

Id |ParentId| Name 
--- |--------|------- 
1 |NULL |A 
2 |1  |B 
3 |2  |C 
4 |3  |D 

AはBの親である、BはCの親であり、Cは、私は両親、各レコードが有してもよいか計算したいD.

の親ですか? 例えば、Bは参照A、Cは参照B、Dは参照Cである。

この場合、親の数に基づいて、Aの深さレベルは0、Bは1、Cは2、Dは3です。持ってる。

再帰関数を使用してこれを行うことができます。レコードに親がある場合は、毎回クエリを実行します。私は効率的な方法でlinqクエリを使用してこれを達成したい。

答えて

0

これを達成するための最善の方法は、複数の要求または一時的なSQLテーブルを一度にすべてのテーブルをDictionaryで選択し、C#側で親カウントを計算することだと思います。

それはあなたのために許容できるなら、それは過度な計算を防ぐために、この機能と追加のクラスを使用して行うことができます

public class ParentInfo 
{ 
    public int? ParentId { get; } 

    public int? ParentCount { get; set; } 

    public ParentInfo(int? parentId) 
    { 
     ParentId = parentId; 
    } 
} 

private static int GetParentCount(int id, IDictionary<int, ParentInfo> conections) 
{ 
    if (!conections.ContainsKey(id)) 
     throw new InvalidDataException($"Id = {id} not found in connections"); 
    var info = conections[id]; 
    if (info.ParentCount.HasValue) return info.ParentCount.Value; 

    var result = 0; 
    if (info.ParentId.HasValue) result += 1 + GetParentCount(info.ParentId.Value, conections); 
    info.ParentCount = result; 
    return result; 
} 

その後、あなたはこのコードを使用して結果を取得することができます

var conections = table.ToDictionary(r => r.Id, r => new ParentInfo(r.ParentId)); 
var result = conections.Select(c => new 
{ 
    Id = c.Key, 
    ParentCount = GetParentCount(c.Key, conections) 
}).ToArray(); 
関連する問題