sql >> Database teknologi >  >> RDS >> Mysql

Forespørgsel:tæl flere aggregater pr. vare

Her er et trick:at beregne en SUM() af værdier, der vides at være enten 1 eller 0, svarer til en COUNT() af rækkerne, hvor værdien er 1. Og du ved, at en boolesk sammenligning returnerer 1 eller 0 (eller NULL).

SELECT c.catname, COUNT(m.catid) AS item_count,
  SUM(i.ownerid = @ownerid) AS owner_item_count
FROM categories c
  LEFT JOIN map m USING (catid)
  LEFT JOIN items i USING (itemid)
GROUP BY c.catid;

Med hensyn til bonusspørgsmålet kan du simpelthen lave en indre joinforbindelse i stedet for en ydre joinforbindelse, hvilket kun vil betyde kategorier med mindst én række i map ville blive returneret.

SELECT c.catname, COUNT(m.catid) AS item_count,
  SUM(i.ownerid = @ownerid) AS owner_item_count
FROM categories c
  INNER JOIN map m USING (catid)
  INNER JOIN items i USING (itemid)
GROUP BY c.catid;

Her er en anden løsning, som ikke er så effektiv, men jeg vil vise den for at forklare, hvorfor du fik fejlen:

SELECT c.catname, COUNT(m.catid) AS item_count,
  SUM(i.ownerid = @ownerid) AS owner_item_count
FROM categories c
  LEFT JOIN map m USING (catid)
  LEFT JOIN items i USING (itemid)
GROUP BY c.catid
HAVING item_count > 0;

Du kan ikke bruge kolonnealiasser i WHERE klausul, fordi udtryk i WHERE klausul evalueres før udtrykkene i valglisten. Med andre ord er de værdier, der er knyttet til valglisteudtryk, ikke tilgængelige endnu.

Du kan bruge kolonnealiasser i GROUP BY , HAVING , og ORDER BY klausuler. Disse klausuler køres, efter at alle udtryk i valglisten er blevet evalueret.



  1. Hvordan ændres den udenlandske nøglehenvisningshandling? (opførsel)

  2. Sådan opdaterer du automatisk data i databasen i PHP

  3. Automatisk stigning med dvale

  4. Hvordan kan jeg lave fatale fejl i ALLE mysql-advarsler?