2017-02-27 10 views
2

登録しているデバイスからトランザクションを作成した一意のユーザーを数えようとしています。ここで最近の日付に基づくカウントsql

は私のクエリです。しかし

select Distinct 
    username , 
    case 
     when user_agent like '%Android%' then 'Android' 
     when user_agent like '%iPhone%' OR user_agent like '%Iphone%' then  'IOS' 
     else 'Internet Banking' 
    end as type, 
    min(time) 
from 
    activeUsers 
group by 
    (1, 2); 

、私はこれを取得、結果セット内:

Image Showing query results

私が欲しいたとえば、ユーザujvs24hxen9 /アブダラが最新に基づいてカウントされます例えば、インターネットバンキングでのみカウントされ、インターネットバンキングやアイオスではカウントされません。

どうすればいいですか?私はpostgresqlを使用しています

ありがとう!

答えて

1

PostgreSQLのDISTINCT ON (username)を使用すると、ユーザーあたり1レコードしか取得できません。独自のクエリについては

select distinct on (username) 
    username, 
    case when user_agent like '%Android%' then 'Android' 
     when user_agent like '%iPhone%' 
     or user_agent like '%Iphone%' then 'IOS' 
     else 'Internet Banking' 
    end as type, 
    time 
from activeusers 
order by username, time desc; 

:ユーザーあたりの目的のレコード(つまり最新の)最初のを取得するためにORDER BY句を使用し

  • GROUP BY xyzあなたはXYZごとに1つの結果行をしたい意味。クエリでは、最初の2つの列でグループ化するので、ユーザーと型ごとに結果行が得られます。しかし、ユーザーあたりの結果行のみが必要です。したがって、あなたのGROUP BY節にタイプを持つことは意味がありません。
  • DISTINCTは、結果から重複する行を削除します。ユーザーとタイプごとにグループ化し、これらの列の両方が選択されると、重複はありません。これらの2つの列はそれぞれの行をすでに区別しているため、DISTINCTをこれらの行に適用することは不必要です。
  • そして、ユーザーあたりの最新の時間を探して、これを使用して目的のレコードにアクセスする場所もありません。だから明らかにこのクエリは機能しません。
+0

私はタイプによってユーザ名やグループ、それらをカウントしたい、このクエリが正常に動作しますが、あなたが上記のクエリの結果を構築することができ –

+0

私は、OSの種類によって、ユーザ名とグループにそれらを数えるカント: 'タイプを選択し、カウント( *)from()xタイプ別のグループ; ' –

1

はこれを試してみてください:

select Distinct username , 
Case When user_agent like '%Android%' then 'Android' 
when user_agent like '%iPhone%' OR user_agent like '%Iphone%' then  'IOS' 
else 'Internet Banking' 
END as type , time 
from activeUsers a1 
where time = (select max(time) from activeUsers a2 where a1.username = a2.username) 

あなたは最大ノー分の時間を意味する「最新」の時間を言うとき、私は想定しています。

0

あなただけのユーザーごとに最後のトランザクションを取得するためにrow_numberウィンドウ関数を使用できます。

SELECT username, type 
FROM (SELECT username , 
       CASE WHEN user_agent LIKE '%Android%' THEN 'Android' 
        WHEN user_agent LIKE '%iPhone%' OR 
         user_agent LIKE '%Iphone%' THEN 'IOS' 
        ELSE 'Internet Banking' 
     END AS type, 
     time 
     ROW_NUMBER() OVER (PARTITION BY username ORDER BY time DESC) AS rn 
FROM activeUsers) t 
WHERE rn = 1 
0

@Mureinikによって与えられた答えの代わりに、各ユーザーの最新の時間を識別するためにサブクエリを使用することですそれを使用して元のテーブルを結果セットに実際に必要なレコードに制限します。

WITH cte AS (
    SELECT username, MAX(time) AS max_time 
    FROM activeUsers 
    GROUP BY username 
) 

SELECT t1.username, 
     CASE WHEN t1.user_agent LIKE '%Android%' THEN 'Android' 
      WHEN t1.user_agent LIKE '%iPhone%' OR t1.user_agent LIKE '%Iphone%' THEN 'IOS' 
      ELSE 'Internet Banking' 
     END AS type 
FROM activeUsers t1 
INNER JOIN cte t2 
    ON t1.username = t2.username AND 
     t1.time  = t2.max_time 
1
select distinct on (username) 
    username, 
    case 
     when user_agent like '%Android%' then 'Android' 
     when user_agent like '%iPhone%' OR user_agent like '%Iphone%' then 'IOS' 
     else 'Internet Banking' 
    end as type 
    time 
from activeUsers 
order by username, time desc 
関連する問題