2015-04-29 1 views
0

Я столкнулся с проблемой в двух частях. Мне было предложено заменить 3 столбца в матрице, которая агрегирует имя в группе строк. 3 столбца находятся за пределами группы столбцов.SSRS - Медиана по группам - Желудочный массив?

Задача 1 - Матрицы хотят суммировать область данных. Кажется, что невозможно показать Raw Data (а затем скрыть его, чтобы эти строки во время выполнения заполнили массив).

Задача 2 - Мне нужно рассчитать медианное имя BY. Это означает, что во время выполнения мне нужно вычислить одну медиану для каждого имени за раз, сбросить массив и начать новую для следующего значения имени, ИЛИ, мне нужен многомерный массив, где каждый порядковый номер сам является массивом, соответствующим к имени.

Я также являюсь общей обезьяной кода в VB.

Вот что я сейчас заимствовал из интернет-сообщения о вычислении медианы в SSRS.

Dim values As System.Collections.ArrayList 

    Function AddValue(ByVal newValue As Decimal) 
     If (values Is Nothing) Then 
      values = New System.Collections.ArrayList() 
     End If 
     values.Add(newValue) 
    End Function 

    Function GetMedian() As Decimal 
     Dim count As Integer = values.Count 
     If (count > 0) Then 
      values.Sort() 
      GetMedian = values(count/2) 
     End If 
    End Function 
+0

Что такое RSBMS? – Hiten004

+0

SQL Server 2012. Я имею в виду ... Я мог бы бросить его в цикл в SQL, но ... Мне очень не нравится RBAR, и это добавит много накладных расходов на запрос. Это может закончиться тем, что, хотя у вас есть только молоток, все выглядит как гвоздь. – tcarper

+1

В функции tsql 'PERCENTILE_CONT' для медианы https://msdn.microsoft.com/en-us/library/hh231473(v=sql.110).aspx – Hiten004

ответ

0

Я думаю, что у меня есть SQL-решение, которое не использует цикл.

;WITH Counts AS 
(
    SELECT SalesPerson, c = COUNT(*) 
    FROM dbo.Sales 
    GROUP BY SalesPerson 
) 
SELECT a.SalesPerson, Median = AVG(0.+Amount) 
FROM Counts a 
CROSS APPLY 
(
    SELECT TOP (((a.c - 1)/2) + (1 + (1 - a.c % 2))) 
     b.Amount, r = ROW_NUMBER() OVER (ORDER BY b.Amount) 
    FROM dbo.Sales b 
    WHERE a.SalesPerson = b.SalesPerson 
    ORDER BY b.Amount 
) p 
WHERE r BETWEEN ((a.c - 1)/2) + 1 AND (((a.c - 1)/2) + (1 + (1 - a.c % 2))) 
GROUP BY a.SalesPerson;