Reputation: 40315
For the T-SQL (SQL Server 2016) bit
type, is there some way to achieve an aggregate equivalent of a logical AND and a logical OR? For example, with this table:
CREATE TABLE #Example (id int, category int, isRed bit, isBlue bit)
INSERT INTO #Example VALUES ( 1, 1, 1, 1)
INSERT INTO #Example VALUES ( 2, 1, 0, 0)
INSERT INTO #Example VALUES ( 3, 1, 1, 0)
INSERT INTO #Example VALUES ( 4, 2, 0, 1)
INSERT INTO #Example VALUES ( 5, 2, 0, 1)
INSERT INTO #Example VALUES ( 6, 2, 0, 1)
I'd like to create a query that lists, per category, if any of isRed
is set (OR), and if all of isBlue
is set (AND), e.g. outputting:
category anyRed allBlue
1 1 0
2 0 1
That is, I'd like something like:
SELECT
category,
OR(isRed) isAnyRed,
AND(isBlue) isAllBlue
FROM
#Example
GROUP BY
category
The only thing I could think of to try was:
SELECT
category,
MAX(isRed) isAnyRed,
MIN(isBlue) isAllBlue
FROM
#Example
GROUP BY
category
Which does not work, giving the error:
Operand data type bit is invalid for max operator.
Similar results occur with all other aggregate functions.
Upvotes: 5
Views: 3049
Reputation: 13959
You can use subquery and find as below:
Select Category, AnyRed = Case When SmRed > 0 then 1 else 0 End,
AllBlue = Case When SmBlue = Cnt then 1 else 0 End from (
select category, SMRed = sum(iif(isred=1,1,0)), SMBlue = Sum(iif(isBlue=1,1,0)), Cnt= Count(id) from #Example
group by category
) a
Upvotes: 2
Reputation: 24903
MIN
and MAX
functions can be used:
SELECT
category,
MAX(CONVERT(tinyint,isRed)) isAnyRed,
MIN(CONVERT(tinyint,isBlue)) isAllBlue
FROM
#Example
GROUP BY
category
But you have to convert bit
to some numeric value (tinyint
), as MIN
and MAX
work only with numbers, not booleans.
Upvotes: 10