Използване на агрегатни функции в HAVING клаузата е много законна, тъй като HAVING елиминира груповите редове. Условно броене може да се постигне или чрез използване на свойството NULL s не се броят:
count(expression)... брой входни редове, за които стойността на израза не е нула
или ако използвате PostgreSQL 9.4 или по-нова версия, с агрегатния FILTER клауза:
count(*) FILTER (WHERE something > 0)
Можете също да използвате сбор от единици (и нули).
PostgreSQL>=9.4 и SQLAlchemy>=1.0.0
Използване на филтрирана агрегатна функция:
.having(func.count(1).filter(Question.accepted) >
func.count(1).filter(not_(Question.accepted)))
По-стари PostgreSQL и/или SQLAlchemy
SQL аналогът за "if" е или CASE израз или в този случай nullif() функция. И двете могат да се използват заедно с факта, че NULL s не се броят:
from sqlalchemy import case
...
.having(func.count(case([(Question.accepted, 1)])) >
func.count(case([(not_(Question.accepted), 1)])))
или:
.having(func.count(func.nullif(Question.accepted, False)) >
func.count(func.nullif(Question.accepted, True)))
Използване на nullif() може да бъде малко объркващо, тъй като "условието" е това, което не искам да преброя. Можете да създадете израз, който да направи условието по-естествено, но това остава за читателя. Тези 2 са по-преносими решения, но от друга страна FILTER Клаузата е стандартна, но не е широко разпространена.