Eug*_*kov 5 postgresql aggregate-functions
我有下一个数据:
id | name | amount | datefrom
---------------------------
3 | a | 8 | 2018-01-01
4 | a | 3 | 2018-01-15 10:00
5 | b | 1 | 2018-02-20
Run Code Online (Sandbox Code Playgroud)
我可以使用下一个查询对结果进行分组:
select name, max(amount) from table group by name
Run Code Online (Sandbox Code Playgroud)
但我也需要id选定的行。因此我尝试过:
select max(id), name, max(amount) from table group by name
Run Code Online (Sandbox Code Playgroud)
正如预期的那样,它返回:
id | name | amount
-----------
4 | a | 8
5 | b | 1
Run Code Online (Sandbox Code Playgroud)
但我需要 id3的数量8:
id | name | amount
-----------
3 | a | 8
5 | b | 1
Run Code Online (Sandbox Code Playgroud)
这可能吗?
附注。这是计费任务所必需的。在某一天的2018-01-15配置a发生了变化,用户消耗了一些资源 10h8和休息天 14h -- 的数量3。我需要用最大值来计算这样的一天。因此,id = 4仅忽略 2018-01-15 天的row with 。(对于第二天 2018-01-16 我将
计费的金额3)
所以我对行进行计费:
3 | a | 8 | 2018-01-01
Run Code Online (Sandbox Code Playgroud)
如果有什么问题的话。我必须报告那一行id == 3是错误的。
但是当我使用聚合函数时,有关的信息id丢失了。
如果可能的话会很棒:
select current(id), name, max(amount) from table group by name
select aggregated_row(id), name, max(amount) from table group by name
Run Code Online (Sandbox Code Playgroud)
这里agg_row指的是聚合函数选择的行max
UPD
我将任务解决为:
SELECT
(
SELECT id FROM t2
WHERE id = ANY ( ARRAY_AGG( tf.id ) ) AND amount = MAX( tf.amount )
) id,
name,
MAX(amount) ma,
SUM( ratio )
FROM t2 tf
GROUP BY name
Run Code Online (Sandbox Code Playgroud)
UPD
使用窗口函数会好得多
至少有3种方法,见下文:
CREATE TEMP TABLE test (
id integer, name text, amount numeric, datefrom timestamptz
);
COPY test FROM STDIN (FORMAT csv);
3,a,8,2018-01-01
4,a,3,2018-01-15 10:00
5,b,1,2018-02-20
6,b,1,2019-01-01
\.
Run Code Online (Sandbox Code Playgroud)
SELECT DISTINCT ON (name)
id, name, amount
FROM test
ORDER BY name, amount DESC, datefrom ASC;
Run Code Online (Sandbox Code Playgroud)
SELECT id, name, amount FROM (
SELECT *, row_number() OVER (
PARTITION BY name
ORDER BY amount DESC, datefrom ASC) AS __rn
FROM test) AS x
WHERE x.__rn = 1;
Run Code Online (Sandbox Code Playgroud)
SELECT id, name, amount FROM test
WHERE id = (
SELECT id FROM test AS t2
WHERE t2.name = test.name
ORDER BY amount DESC, datefrom ASC
LIMIT 1
);
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1012 次 |
| 最近记录: |