MSSQL:从 Session 出勤数据中识别群组

MSSQL: identify Cohorts from Session Attendance data

我有按主题划分的 session 组出席率数据,其中一行是一个用户在给定的 date/time 上参加 session。一组产品可以有一定数量的 session,例如10,它们通常在同一时间 (StartTime) 和星期几 (DayOfWeek) 提供。

我想确定团体发售的开始和结束日期,即给定群组的第一个 session 和最后一个 session。群组将从参加群组 session 的相同用户列表中确定。

Table: ---GroupSessions--- GroupSessionDate UserID Topic StartTime DayOfWeek ArrivalStatus Jan-08-2015 1 A 11:30:00 AM Thursday Arrived Jan-08-2015 2 A 11:30:00 AM Thursday Arrived Jan-08-2015 3 A 11:30:00 AM Thursday Arrived Jan-08-2015 4 A 11:30:00 AM Thursday Arrived Jan-15-2015 1 A 11:30:00 AM Thursday Arrived Jan-15-2015 2 A 11:30:00 AM Thursday Arrived Jan-15-2015 3 A 11:30:00 AM Thursday Arrived Jan-15-2015 4 A 11:30:00 AM Thursday Arrived Jan-22-2015 1 A 11:30:00 AM Thursday Arrived Jan-22-2015 2 A 11:30:00 AM Thursday Arrived Jan-22-2015 3 A 11:30:00 AM Thursday Arrived Jan-22-2015 4 A 11:30:00 AM Thursday Missed May-15-2015 5 A 09:00:00 AM Friday Arrived May-15-2015 2 A 09:00:00 AM Friday Arrived May-15-2015 6 A 09:00:00 AM Friday Arrived May-22-2015 5 A 09:00:00 AM Friday Arrived May-22-2015 6 A 09:00:00 AM Friday Arrived May-22-2015 2 A 09:00:00 AM Friday Missed May-29-2015 5 A 09:00:00 AM Friday Arrived May-29-2015 6 A 09:00:00 AM Friday Arrived May-29-2015 2 A 09:00:00 AM Friday Missed

在上面的示例中,有 2 个同类群组。同类群组 1 将由用户 1、2、3 和 4 组成,几乎所有人都在 2015 年 1 月 8 日至 2015 年 1 月 22 日期间参加了小组课程(主题 A)。参加 Jan-15-2015 session 和 Jan-08-2015 session 的用户相同,几乎所有人都参加了 Jan-22-2015 session。

同类群组 2(也针对主题 A)由用户 2、5、6 组成,发售日期为 2015 年 5 月 15 日至 29 日。

session 的数量不是按产品设置的,因为它会根据需求而变化,所以我无法考虑从产品日期开始的 session 的数量。

我看过 Oracle/SQL: Split two inter-related lists into independent cohorts 但问题仍未得到解答。

通常我会进行视觉检查并将用户分配到同类群组,但我有数万行,并且希望有一种更有效的方法来使用 SQL 来完成这项工作。我是 运行 女士 SQL 2014.

我已经尝试将 OUTER APPLY 与 table 一起使用,但我并没有真正得到我想要的结果。

你能给我指明正确的方向吗?

SQL:

</p> <pre><code>SELECT src.UserID ,src.GroupSessionDate ,src.StartTime ,src.DayofWeek ,src.Topic ,prevsessdata.GroupSessionDate FROM GroupSessions src OUTER APPLY (SELECT TOP 1 * GroupSessions prevsd WHERE src.Topic=prevsd.Topic AND src.UserID=prevsd.UserID AND src.DayOfWeek=prevsd.DayOfWeek AND src.StartTime=prevsd.StartTime AND prevsd.GroupSessionDate<src.GroupSessionDate) prevsessdata

编辑: 可以做出的假设:

期望的输出: 对于每个主题、开始时间和 DoW,列出队列 Start/End 日期。

谢谢!

我想你正在寻找这样的东西:

; WITH T AS (
    SELECT CONVERT(DATE, REPLACE(GroupSessionDate, '-', ' ')) GroupSessionDate, Topic, StartTime, [DayOfWeek]
        , STUFF((SELECT ', ' + CONVERT(NVARCHAR, UserID)
            FROM GroupSessions
            WHERE GroupSessionDate = G.GroupSessionDate
            AND Topic = G.Topic
            AND StartTime = G.StartTime
            AND [DayOfWeek] = G.[DayOfWeek]
            ORDER BY UserID
            FOR XML PATH ('')), 1, 2, '') [Cohort]
    FROM GroupSessions G
    GROUP BY GroupSessionDate, Topic, StartTime, [DayOfWeek])
SELECT Cohort, MIN(GroupSessionDate) SessionStartDate, MAX(GroupSessionDate) SessionEndDate, Topic, StartTime, [DayOfWeek]
FROM T
GROUP BY Topic, StartTime, [DayOfWeek], Cohort, DATEDIFF(dd, 0, GroupSessionDate) % 7
ORDER BY MIN(GroupSessionDate)

一个简单的group by语句。确实,从您的要求来看,您需要做的就是按主题、开始时间、星期几和 groupsessiondate 分组以找到每个 "cohort" 然后再次对其进行排序以找到每个的最小/最大日期这些。

如果这没有产生正确的结果,您可能需要使用其他一些标准来进一步缩小范围。