1

平均の計算に使用する行を制限したいクエリ (postgresql) があります。

SELECT username,avg(income),count(*) FROM
       Events 
WHERE to_timestamp(eventtimestamp)  >=  '2008-02-23' AND 
      to_timestamp(eventtimestamp) <=   '2009-01-03' and username='Joe'
GROUP BY userid 

Joe には 40 のエントリがありますが、収入の平均を計算するために使用される行数を制限したいと考えています。クエリの最後に追加できるlimit関数を認識していますが、これは、クエリの先頭にあるaverageコマンドによって考慮される行ではなく、クエリ全体の出力を制限します。avg に最初の n 行のみを使用するように指示する方法はありますか?

例:機能しない

SELECT username,avg(income) limit 5,count(*) FROM
       Events 
WHERE to_timestamp(eventtimestamp)  >=  '2008-02-23' AND 
      to_timestamp(eventtimestamp) <=   '2009-01-03' and username='Joe'
GROUP BY userid 

最初の 5 行だけを平均化します。

ありがとう!

4

5 に答える 5

3

2つの理由から回答を追加しています。まず、他の回答のほとんどは、質問の一部ではないcount(*)およびに影響します。avg()第 2 に、これを複数のユーザーに対して実行したい場合があります。

したがって、次のことを試すことができます。

SELECT username, avg(case when seqnum <= 40 then income end), count(*)
FROM (select e.*, ROW_NUMBER() over (partition by username order by eventtimestamp desc) as seqnum
      from Events e
      WHERE to_timestamp(eventtimestamp)  >=  '2008-02-23' AND 
            to_timestamp(eventtimestamp) <=   '2009-01-03'
     ) e
GROUP BY username
于 2013-04-16T13:23:34.253 に答える
2

内部クエリの平均を取ることができます:

SELECT username,avg(income),count(*)
FROM (
  SELECT username, income
  FROM Events 
  WHERE to_timestamp(eventtimestamp) BETWEEN '2008-02-23' AND '2009-01-03'
  and username='Joe'
  LIMIT 5) x
GROUP BY userid;

を使用して単純化することにも注意してくださいBETWEEN

于 2013-04-16T12:15:45.480 に答える
1

たまたま、現在の行で終了する 5 行の平均を好む (または気にしない) 場合は、ウィンドウ関数を使用して副選択を回避できます。

select
    username,
    avg(income) over(rows 4 preceding),
    count(*)
from events 
where to_timestamp(eventtimestamp)  >=  '2008-02-23' and 
      to_timestamp(eventtimestamp) <=   '2009-01-03' and username='joe'
group by userid

あなたのコメントを理解していれば、実際にcountウィンドウ関数として使用できます。

    count(*) over(rows 4 preceding)

または、null をカウントしたくない場合:

    count(income) over(rows 4 preceding)
于 2013-04-16T13:05:04.120 に答える