Выполнение побитовой суммы - PullRequest
10 голосов
/ 14 декабря 2010

Как часть сложного агрегата, я хочу знать побитовую сумму некоторых данных, т.е. если у меня есть строки со значениями 1,1,1,2,2,8, то побитовая сумма равна 11. В этом случае все значения представляют собой точные степени двух (единичные биты), поэтому я могу взломать их, сгруппировав и суммировав по группам (очевидно, этот пример немного мучителен по сравнению с реальным запросом):

select SUM(y.test)
from (
    select x.test
    from ( -- garbage test data
        select 1 as [test]
        union all select 1
        union all select 1
        union all select 2
        union all select 2
        union all select 8) x
group by x.test) y

но есть ли чистый способ выполнить побитовую сумму в [T] SQL?

Ответы [ 4 ]

18 голосов
/ 14 декабря 2010

Если все ваши тестовые значения являются единичными битами, как в вашем примере (1, 2, 8) - просто используйте SUM(DISTINCT col) в вашем запросе.

Надеюсь, что это поможет.

(Для справки: http://msdn.microsoft.com/en-us/library/ms187810.aspx)

3 голосов
/ 14 декабря 2010

Это немного запутанно, но это делает то, что вам нужно (обратите внимание, что я включил бит до 128, вам может потребоваться подняться выше, или, возможно, не нужно подняться выше 8).

with data(i)
AS
(
    select 1 
        union all select 1
        union all select 1
        union all select 2
        union all select 2
        union all select 8
)
SELECT MAX(i & 1) +
MAX(i & 2) +
MAX(i & 4) +
MAX(i & 8) +
MAX(i & 16) +
MAX(i & 32) +
MAX(i & 64) +
MAX(i & 128)
from data

который, очевидно, может быть преобразован в UDF, если вы того пожелаете.

0 голосов
/ 07 июля 2016

Для отдельных битов SUM (столбец DISTINCT) является лучшим ответом, но для нескольких битов, таких как 3 (= 1 | 2), это не сработает, и лучший и более быстрый ответ будет выглядеть так:(DISTINCT X.Text & TB) ОТ X перекрестного соединения (значения (1), (2), (4), (8), (16), (32), (64), (128), (256),(512)) T (B)

0 голосов
/ 14 декабря 2010

У вас есть оператор | который выполняет поразрядно или для 2 операндов. Можно решить вашу проблему с помощью курсора и этого оператора.

Редактировать да я перепутал и и или исправил.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...