2012-04-20 13 views
3

ID,Amount、およびParent_IDを含む1つのテーブルがあります。 (現実にはもう少し複雑ですが、これはこの例ではすべて重要な列です)。基本的に私がやりたいことは、Amount列をグループ化し、最も一般的な親(つまり親IDがNULLのもの)で合計することです。最も低い共通の親のIDでのMySQLグループ

ID Amount Parent_ID 
1 100  NULL 
2 150  1 
3 50  1 
4 75  3 
5 25  4 
6 125  NULL 
7 50  6 
8 50  7 
9 100  8 

期待される結果:

ID SUM 
1 400 
6 325 

あなたが見ることができるように、それは彼らだけがトップレベルの項目ある意味、二つのレコード、親を持っていけないものをretuns。 Sumの列はすべての子のAmountを再帰的に合計したものなので、ID = 1は1,2,3,4と5の合計です。ID = 6は6,7,8,9の合計です。

+0

ネスト数は設定されていますか?あなたは5時に停止しますか、それとも永遠に続くことができますか? – xQbert

+0

理論的には永遠に進むことができますが、解決策がない場合は永遠に私は1つしか取ることができないと思います。 – user380527

+0

テスト用セットアップ環境:http://www.sqlfiddle.com/#!2/b7a79 – mellamokb

答えて

6

あなたhierarcyのレベル数に制限を定義することができる場合、あなたはレベルの任意の数にこのソリューションを拡張することができます。

select 
    coalesce(t5.ID,t4.ID,t3.ID,t2.ID,t1.ID) as Root, 
    sum(t1.Amount) as Amount 
from Table1 t1 
left join Table1 t2 on t1.Parent_ID = t2.ID 
left join Table1 t3 on t2.Parent_ID = t3.ID 
left join Table1 t4 on t3.Parent_ID = t4.ID 
left join Table1 t5 on t4.Parent_ID = t5.ID 
group by Root 

ただ、必要に応じてleft joinより多くを追加し、リストに追加​​3210の列の

デモ:http://www.sqlfiddle.com/#!2/b7a79/17

+1

素晴らしい答え。私はあなたに+2を与えたいと思います。 1つは合体のためのもので、私はこれまでに見たことがないものとsqlfiddleのために+1を追加しました。なんと素晴らしいツールです! – barsju

+1

これは良い回避策ですが、私はそれに奇妙なバグがあります。私のテーブルには私もクエリと一緒に選択したい名前の列があります。問題は、名前を選択すると間違っている(選択した名前がルートIDを持つアイテムの名前と同じではない)ということです。次の例を参照してください(これを実現するために挿入物を再配置しなければならないことに注意してください)。http://www.sqlfiddle.com/#!2/dbd58/1 – user380527

+1

名前をまとめる必要がありません。 '合致(t5.Name、t4.Name、t3.Name、t2.Name、t1.Name)をName'とします。 http://www.sqlfiddle.com/#!2/dbd58/4 – user380527

0

あなたが探しているものを達成するには、構造の深さを制限するものを望まないため、再帰的なストアドプロシージャが必要です。

データ構造を変更する方が簡単だと思います。各子を最上位の親に関連付ける列を追加します。そうすれば、単純なGROUP BYであなたが望むものを手に入れることができます。

関連する問題