У меня есть набор данных, который организован следующим образом:
Timestamp|A0001|A0002|A0003|A0004|B0001|B0002|B0003|B0004 ...
---------+-----+-----+-----+-----+-----+-----+-----+-----
2008-1-1 | 1 | 2 | 10 | 6 | 20 | 35 | 300 | 8
2008-1-2 | 5 | 2 | 9 | 3 | 50 | 38 | 290 | 2
2008-1-4 | 7 | 7 | 11 | 0 | 30 | 87 | 350 | 0
2008-1-5 | 1 | 9 | 1 | 0 | 25 | 100 | 10 | 0
...
Где A0001 - это значение A элемента № 1, а B0001 - это значение B элемента № 1. В таблице может быть более 60 различных элементов, и каждый элемент имеет столбец значения A и столбец значения B, что означает в общей сложности более 120 столбцов в таблице.
Я хочу получить результат из трех столбцов (индекс элемента, значение A, значение B), в котором суммируются значения A и B для каждого элемента:
Index | A Value | B Value
------+---------+--------
0001 | 14 | 125
0002 | 20 | 260
0003 | 31 | 950
0004 | 9 | 10
....
Когда я буду переходить от столбцов к строкам, я ожидаю, что в решении появится ось, но я не уверен, как ее конкретизировать. Частично проблема заключается в том, как выделить A и B для формирования значений для столбца Index. Другая часть заключается в том, что мне никогда раньше не приходилось использовать Pivot, поэтому я спотыкаюсь и о базовом синтаксисе.
Я думаю, что в конечном итоге мне нужно многоэтапное решение, которое сначала строит суммирование как:
ColName | Value
--------+------
A0001 | 14
A0002 | 20
A0003 | 31
A0004 | 9
B0001 | 125
B0002 | 260
B0003 | 950
B0004 | 10
Затем измените данные ColName, чтобы убрать индекс:
ColName | Value | Index | Aspect
--------+-------+-------+-------
A0001 | 14 | 0001 | A
A0002 | 20 | 0002 | A
A0003 | 31 | 0003 | A
A0004 | 9 | 0004 | A
B0001 | 125 | 0001 | B
B0002 | 260 | 0002 | B
B0003 | 950 | 0003 | B
B0004 | 10 | 0004 | B
Наконец, само присоединение позволяет переместить значения B рядом со значениями A.
Кажется, это долгий процесс получения того, что я хочу. Поэтому мне нужен совет относительно того, направляюсь ли я по правильному пути, или есть другой подход, который я упустил, который сделает мою жизнь намного проще.
Примечание 1) Решение должно быть в T-SQL на MSSQL 2005.
Примечание 2) Формат таблицы не может быть изменен.
Редактировать В другом методе, о котором я думал, используются UNION и отдельные SUM () в каждом столбце:
SELECT '0001' as Index, SUM(A0001) as A, SUM(B0001) as B FROM TABLE
UNION
SELECT '0002' as Index, SUM(A0002) as A, SUM(B0002) as B FROM TABLE
UNION
SELECT '0003' as Index, SUM(A0003) as A, SUM(B0003) as B FROM TABLE
UNION
SELECT '0004' as Index, SUM(A0004) as A, SUM(B0004) as B FROM TABLE
UNION
...
Но этот подход тоже выглядит не очень хорошо
РЕДАКТИРОВАТЬ Пока есть 2 отличных ответа. Но я бы хотел добавить в запрос еще два условия :-)
1) Мне нужно выбрать строки на основе диапазона временных меток (minv
2) Мне также нужно условно выбрать строки в UDF, который обрабатывает метку времени
Используя имена таблиц Бреттского, вышеприведенные слова переведут в:
...
(SELECT A0001, A0002, A0003, B0001, B0002, B0003
FROM ptest
WHERE timestamp>minv AND timestamp<maxv AND fn(timestamp)=fnv) p
unpivot
(val for item in (A0001, A0002, A0003, B0001, B0002, B0003)) as unpvt
...
Учитывая, что я условно добавил требование fn (), я думаю, что мне также нужно идти по динамическому пути SQL, предложенному Джонатоном. Тем более, что мне нужно создать один и тот же запрос для 12 разных таблиц - все в одном стиле.