2016-11-09 15 views
0

日記表があるとします。日記の各エントリはuser_identry_dateです。 user_idの範囲については、指定した日付より後の最初のエントリを選択したいと考えています。すべての行について、基準を満たす最初のエントリを選択します。

ので

user_id | entry_date 
-------------------- 
    1  | 2016-11-09 20:00:00 
    2  | 2016-11-09 20:00:00 
    1  | 2016-11-09 21:00:00 
    1  | 2016-11-09 22:00:00 
    5  | 2016-11-10 20:00:00 

と私は

SELECT user_id,entry_date FROM entries 
WHERE entries.user_id BETWEEN 10 AND 20 
AND TAKE_FIRST(entries.entry_date >= to_timestamp('2016-11-09 20:30:00', 'yyyy-mm-dd hh24:mi:ss')) 

ような何か書くことができます想像(TAKE_FIRST()は、私にはわからない何のためのプレースホルダです。)

となり、結果はとなる

user_id | entry_date 
-------------------- 
    1  | 2016-11-09 21:00:00 
    5  | 2016-11-10 20:00:00 

どのようにすればいいですか? ROW_NUMBER()

答えて

1

:それぞれのuser_idに対して

SELECT user_id,entry_date 
FROM (
    SELECT user_id,entry_date, 
      ROW_NUMBER() OVER(PARTITION BY user_id ORDER BY entry_date) as rnk 
    FROM entries 
    WHERE entries.user_id BETWEEN 10 AND 20 
     AND entries.entry_date >= to_timestamp('2016-11-09 20:30:00', 'yyyy-mm-dd hh24:mi:ss') 
    ) 
WHERE rnk = 1 
+0

パフォーマンスに問題があり、指定された日付よりも大きいすべてのタイムスタンプが選択され、そのうちの1つだけが選択されていると思います。パフォーマンスを改善できますか? – kasperhj

2
SELECT user_id,MIN(entry_date) FROM entries 
WHERE entries.user_id BETWEEN 10 AND 20 
AND entry_date >= to_timestamp('2016-11-09 20:30:00', 'yyyy-mm-dd hh24:mi:ss')) 
GROUP BY user_id 

範囲では、お好みのものよりも大きい最小の日付を検索します。 entriesテーブルの追加データが必要な場合は機能しませんが、それ以外の場合は最も簡単な解決策になります。

+0

窓関数なしで解けるのは良い目、+1。それは言われている、もし彼がより多くの列を望むなら、それはしないでしょう:) – sagi

+0

@サギ - 彼がもっと多くの列を望むなら、それは 'keep(dense_rank first/last order by entry_date)'のためです! – mathguy

+0

はい、彼は窓関数を使用する場合、それはあなたがそれを行う方法を知っているように見えますか?..私は、最初のエントリからのより多くの列が必要な場合、作業。 @mathguy – sagi

関連する問題