简体   繁体   中英

SQL query to find matching subsets

I have a table Students(StudentID, classes, school, advisor) and I need to find a pair of students that take exactly the same set of classes.

For example, in a table:

在此处输入图片说明

I would have an output:

S3678 and S8978

Because they are both taking the same number of classes (2), and set of classes, French and Logic.

Using T-SQL (initial answer was without knowledge of DBMS the OP was using...):

I would use a common table expression to solve this:

;WITH cte AS (
    SELECT StudentID, COUNT(Classes) numOfClassesTaken, 
        STUFF((SELECT DISTINCT ', ' + Classes
               FROM Students s2
               WHERE s2.StudentID = s1.StudentID
               ORDER BY ', ' + Classes
               FOR XML PATH('')), 1, 2, '') as ClassList
    FROM Students s1
    GROUP BY StudentID)
, matchingClasses AS (
    SELECT numOfClassesTaken, ClassList
    FROM cte
    GROUP BY numOfClassesTaken, ClassList
    HAVING COUNT(*) > 1)

SELECT t1.StudentID, t1.ClassList 
FROM cte t1
INNER JOIN matchingClasses t2 ON t1.numOfClassesTaken = t2.numOfClassesTaken AND t1.ClassList = t2.ClassList

在此处输入图片说明

[DEMO HERE]

  • If in postgre8.4+, then use the function "array_agg"
  • If this is in mySql5.6, then change array_agg() to GROUP_CONCAT(classes).
  • If question is in Oracle, then change GROUP_CONCAT() to COLLECT.
 select t1.studentid from (select studentid, array_agg(classes) as classes_set from (select studentid, classes from students order by studentid, classes) as st1 group by studentid) t1 join (select studentid, array_agg(classes) as classes_set from (select studentid, classes from students order by studentid, classes) as st2 group by studentid) t2 on t1.classes_set=t2.classes_set and t1.studentid <> t2.studentid Result: studentid S8978 S3678

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM