別の更新: 誤って(コピー&ペーストによる)starttime = ... or starttime = ...
がありました ただし、starttime = ... or endtime = ...
である必要があります
更新:
私のクエリをより詳細に説明するには(最後のクエリにはさらに多くのコメントがあります):
まず、単純に
SELECT
...
FROM gc_sessions s
WHERE DATE(starttime) = CURDATE() OR DATE(endtime) = CURDATE()
これは、「セッションが今日開始または終了したすべてのユーザーを教えてください」と言っているようなものではありません。これらを何度も何度も検討する必要があるため、クエリは少し不器用になりますが、実際にはそれほど複雑ではありません。
したがって、通常はCOUNT()関数を使用して何かをカウントしますが、「条件付きカウント」が必要なため、SUM()関数を使用して、1を追加する場合と追加しない場合を指定します。
SUM (CASE WHEN ... THEN 1 ELSE 0 END) AS a_column_name
SUM()関数は、今日からのセッションの結果セットの各行を調べます。したがって、この結果セットの各ユーザーについて、指定した日付にこのユーザーがオンラインであったかどうかを確認します。オンラインの回数は関係ないため、パフォーマンス上の理由から、EXISTS
を使用します。 。 EXISTS
を使用 何かが見つかるとすぐに停止するサブクエリを指定できるため、NULL
でない限り、何かが見つかったときに何が返されるかは関係ありません。 。だから私が1
を選んだ理由を混乱させないでください 。サブクエリでは、現在外部クエリから検査されているユーザーを内部クエリ(サブクエリ)のユーザーに接続し、時間枠を指定する必要があります。すべての基準がカウント1を満たしている場合、それ以外の場合は前に説明したように0です。
SUM(CASE WHEN
EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 1 DAY)
OR (date(endtime) = CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS todayAndYesterday,
次に、条件と出来上がりごとに列を作成します。1つのクエリで必要なものがすべて揃っています。したがって、更新された質問で基準が変更されたため、ルールを追加する必要があります。
SELECT
/*this is like before*/
SUM(CASE WHEN
EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 1 DAY)
OR (date(endtime) = CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS FridayAndThursday,
SUM(CASE WHEN
EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 2 DAY)
OR (date(endtime) = CURDATE() - INTERVAL 2 DAY)))
/*this one here is a new addition, since you don't want to count the users that were online yesterday*/
AND NOT EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 1 DAY)
OR (date(endtime) = CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS FridayAndWednesdayButNotThursday,
SUM(CASE WHEN
EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 3 DAY) /* minus 3 days to get tuesday*/
OR (date(endtime) = CURDATE() - INTERVAL 3 DAY)))
/*this is the same as before, we check again that the user was not online between today and tuesday, but this time we really use BETWEEN for convenience*/
AND NOT EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) BETWEEN CURDATE() - INTERVAL 2 DAY AND CURDATE() - INTERVAL 1 DAY)
OR (date(endtime) BETWEEN CURDATE() - INTERVAL 2 DAY AND CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS FridayAndTuesdayButNotThursdayAndNotWednesday,
.../*and so on*/
FROM gc_sessions s
WHERE DATE(starttime) = CURDATE() OR DATE(endtime) = CURDATE()
だから、私はあなたが今アイデアを得ることを願っています。他に質問は?遠慮なく尋ねてください。
更新の終了
以前のバージョンの質問への回答:
select
SUM(CASE WHEN EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) = CURDATE() - INTERVAL 1 DAY)
OR (date(starttime) = CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS todayAndYesterday,
SUM(CASE WHEN EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) BETWEEN CURDATE() - INTERVAL 2 DAY AND CURDATE() - INTERVAL 1 DAY)
OR (date(starttime) BETWEEN CURDATE() - INTERVAL 2 DAY AND CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS todayAndYesterdayOrTheDayBeforeYesterday,
SUM(CASE WHEN EXISTS (SELECT 1 FROM gc_sessions sub_s WHERE s.user = sub_s.user
AND ((date(starttime) BETWEEN CURDATE() - INTERVAL 7 DAY AND CURDATE() - INTERVAL 1 DAY)
OR (date(starttime) BETWEEN CURDATE() - INTERVAL 7 DAY AND CURDATE() - INTERVAL 1 DAY)))
THEN 1 ELSE 0 END) AS todayAndWithinTheLastWeek
from gc_sessions s
where date(starttime) = CURDATE()
or date(endtime) = CURDATE()