Sql-Server
將值分組到桶中
我正在查詢,我不確定我目前的方法是否是“最佳”方法。我得到了一個充滿值的表格和一個帶有用於對這些值進行分組的儲存桶的表格。
有 2 種類型的桶:
- 優先級儲存桶,如果項目適用於它們應該落入此儲存桶並被排除在任何後續儲存桶中的條件。
- 一個簡單的範圍桶,值應該在一個範圍內。
我設置了一個可以用來測試的簡化版本。此處的
[Filter]
列#tempBUcket
用於優先級儲存桶表定義
create table #TempData([Id] int, [value] int); create table #TempBucket([Id] int, [FromVal] int,[ToVal] int,[Filter] int);
一些測試數據
INSERT INTO #TempData (Id,value) VALUES (1,1),(2,2),(3,3),(4,4),(5,5), (6,6),(7,7),(8,8),(9,9),(10,1), (11,2),(12,3),(13,4),(14,5),(15,6), (16,7),(17,8),(18,9),(19,10),(20,11); INSERT INTO #TempBucket(Id,FromVal,ToVal,Filter) VALUES (1,0,3,0),(2,3,6,0), (3,6,9,0),(4,9,12,0), (5,NULL,NULL,1),(6,NULL,NULL,2);
現在我有這個查詢,它可以工作並給出我想要的結果,但我覺得這可以做得更好、更有效。
WITH filteredData as (SELECT tv.*,COALESCE(tb1.Id,tb2.Id) as BucketId FROM #TempData tv LEFT JOIN #TempBucket tb1 --prio bucket join ON tb1.Filter IS NOT NULL AND tb1.Filter = tv.Value LEFT JOIN #TempBucket tb2 --range bucket join ON tb2.Fromval < tv.value AND tv.value <= tb2.ToVal ) SELECT Count(fd.value) as count ,BucketId FROM filteredData fd GROUP BY BucketId;
scan
我的解決方案只做 1#TempBucket
但它增加了一個額外的sort
,我不確定它是否更有效,你應該對大量數據進行測試:;with cte as ( select t.*, tb.id as BucketId, row_number() over(partition by t.id order by tb.FromVal) as rn from #TempData t join #TempBucket tb on (t.value = tb.filter) or (tb.Fromval < t.value AND t.value <= tb.ToVal) ) select count(id) as cnt, BucketId from cte where rn = 1 group by BucketId;
要優先考慮其中的行,在優先級儲存桶的情況下為空,或者您可以排序
priority bucket
,我只是不知道是或tb.FromVal``tb.Filter desc``priority bucket``FromVal,ToVal``null``Filter = 0