MySQL Count filas de otra tabla para cada registro en la tabla

20
SELECT
  student.StudentID,
  student.`Name`,
  COUNT(attendance.AttendanceID) AS Total
FROM
  student
LEFT JOIN attendance ON student.StudentID = attendance.StudentID

Estoy tratando de contar la última fila pero en su lugar cuenta todos los resultados y devuelve un resultado

Estoy obteniendo algo como

ingrese la descripción de la imagen aquí

ya que hay varios registros porque hay dos entradas en la ID de asistencia para K1052280, quiero contarlas y devolver el número. Algo como

ingrese la descripción de la imagen aquí

Ali Shaikh
fuente

Respuestas:

23

Te estás perdiendo el GROUP BY

SU CONSULTA CON GRUPO POR

SELECT
  student.StudentID,
  student.`Name`,
  COUNT(attendance.AttendanceID) AS Total
FROM
  student
LEFT JOIN attendance ON student.StudentID = attendance.StudentID
GROUP BY student.StudentID,student.`Name`;

DATA DE MUESTRA

DROP DATABASE IF EXISTS alishaikh; CREATE DATABASE alishaikh;
USE alishaikh
CREATE TABLE student
(
  StudentID CHAR(8) NOT NULL,
  Name VARCHAR(40),
  PRIMARY KEY (StudentID)
);
INSERT INTO student (StudentID,Name) VALUES
('k1052280','Ali Shaikh'),('k1052287','McKenzie Roth'),
('k1052288','Dacey Sullivan'),('k1052294','Zelda Cantu'),
('k1052295','Kimberly Melton'),('k1052296','Tatianna Cantrell'),
('k1052297','Morgan Thornton'),('k1052298','Allistair Barlow'),
('k1052299','Troy Fulton');
CREATE TABLE attendance
(
  AttendanceID INT NOT NULL AUTO_INCREMENT,
  StudentID CHAR(8) NOT NULL,
  PRIMARY KEY (AttendanceID),
  KEY (StudentID)
);
INSERT INTO attendance (StudentID) VALUES
('k1052280'),('k1052280'),('k1052287'),('k1052287'),
('k1052288'),('k1052295'),('k1052295'),('k1052295');

MUESTRA DE DATOS CARGADOS

mysql> DROP DATABASE IF EXISTS alishaikh; CREATE DATABASE alishaikh;
Query OK, 2 rows affected (0.01 sec)
Query OK, 1 row affected (0.00 sec)
mysql> USE alishaikh
Database changed
mysql> CREATE TABLE student
    -> (
    ->   StudentID CHAR(8) NOT NULL,
    ->   Name VARCHAR(40),
    ->   PRIMARY KEY (StudentID)
    -> );
Query OK, 0 rows affected (0.03 sec)

mysql> INSERT INTO student (StudentID,Name) VALUES
    -> ('k1052280','Ali Shaikh'),('k1052287','McKenzie Roth'),
    -> ('k1052288','Dacey Sullivan'),('k1052294','Zelda Cantu'),
    -> ('k1052295','Kimberly Melton'),('k1052296','Tatianna Cantrell'),
    -> ('k1052297','Morgan Thornton'),('k1052298','Allistair Barlow'),
    -> ('k1052299','Troy Fulton');
Query OK, 9 rows affected (0.00 sec)
Records: 9  Duplicates: 0  Warnings: 0

mysql> CREATE TABLE attendance
    -> (
    ->   AttendanceID INT NOT NULL AUTO_INCREMENT,
    ->   StudentID CHAR(8) NOT NULL,
    ->   PRIMARY KEY (AttendanceID),
    ->   KEY (StudentID)
    -> );
Query OK, 0 rows affected (0.02 sec)

mysql> INSERT INTO attendance (StudentID) VALUES
    -> ('k1052280'),('k1052280'),('k1052287'),('k1052287'),
    -> ('k1052288'),('k1052295'),('k1052295'),('k1052295');
Query OK, 8 rows affected (0.00 sec)
Records: 8  Duplicates: 0  Warnings: 0

SU CONSULTA CON GRUPO POR EJECUTADO

mysql> SELECT
    ->   student.StudentID,
    ->   student.`Name`,
    ->   COUNT(attendance.AttendanceID) AS Total
    -> FROM
    ->   student
    -> LEFT JOIN attendance ON student.StudentID = attendance.StudentID
    -> GROUP BY student.StudentID,student.`Name`;
+-----------+-------------------+-------+
| StudentID | Name              | Total |
+-----------+-------------------+-------+
| k1052280  | Ali Shaikh        |     2 |
| k1052287  | McKenzie Roth     |     2 |
| k1052288  | Dacey Sullivan    |     1 |
| k1052294  | Zelda Cantu       |     0 |
| k1052295  | Kimberly Melton   |     3 |
| k1052296  | Tatianna Cantrell |     0 |
| k1052297  | Morgan Thornton   |     0 |
| k1052298  | Allistair Barlow  |     0 |
| k1052299  | Troy Fulton       |     0 |
+-----------+-------------------+-------+
9 rows in set (0.00 sec)

mysql>

DARLE UNA OPORTUNIDAD !!!

RolandoMySQLDBA
fuente
Gracias por esta explicación clara. Ahora, una pregunta más. ¿Cómo puedo ordenar la tabla en Total o filtrar los registros donde Total = 0?
Zonker.in.Geneva
agregar order by Totaldespués del grupo por
PSN
@PSN Gracias por el recordatorio. En la mayoría de los casos, GROUP BYestablece el valor predeterminado para ORDER BY. A veces no. ¡Entonces, ORDER BYtambién podría usarse!
RolandoMySQLDBA
@RolandoMySQLDBA, lamento conectarme con esta respuesta lúcida, ¡con la esperanza de encontrar una solución a mi problema! Supongamos que hay una tercera tabla, TestResultcon columnas de (StudentID, Result). Deseo unirme TestResulty eventualmente obtener COUNT(TestResult.Result)para cada estudiante. Por alguna razón, obtengo valores en exceso para COUNT, mientras que el uso de subconsultas devolvió los COUNT correctos.
Ifedi Okonkwo
Para ayudar a aclarar, mi consulta es así: stackoverflow.com/a/24727261/2554788 , pero sin las DISTINCTpalabras clave. ¿Cuál sería una razón para que los COUNT devuelvan algo diferente (generalmente más alto y, por supuesto, incorrecto) que el patrón de subconsulta?
Ifedi Okonkwo