比较两个时间戳的值并将它们放在结果的两列中
Compare values of two timestamps and put them in two columns in results
CREATE TABLE operations (
id SERIAL PRIMARY KEY,
time_stamp DATE,
product VARCHAR,
plan_week VARCHAR,
quantity DECIMAL
);
INSERT INTO operations
(time_stamp, product, plan_week, quantity
)
VALUES
('2020-01-01', 'Product_A', 'CW01', '125'),
('2020-01-01', 'Product_B', 'CW01', '300'),
('2020-01-01', 'Product_C', 'CW08', '700'),
('2020-01-01', 'Product_D', 'CW01', '900'),
('2020-01-01', 'Product_G', 'CW05', '600'),
('2020-01-01', 'Product_J', 'CW01', '465'),
('2020-03-15', 'Product_A', 'CW01', '570'),
('2020-03-15', 'Product_C', 'CW02', '150'),
('2020-03-15', 'Product_E', 'CW02', '325'),
('2020-03-15', 'Product_G', 'CW01', '482'),
('2020-03-15', 'Product_J', 'CW12', '323');
预期结果:
time_stamp | product | plan_week | quantity | first_plan | last_plan |
---------- |-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_A | CW01 | 125 | CW01 | CW01 |
2020-03-15 | Product_A | CW01 | 570 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_B | CW01 | 300 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_C | CW08 | 700 | CW08 | CW02 |
2020-03-15 | Product_C | CW02 | 150 | CW08 | CW02 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_D | CW01 | 900 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-03-15 | Product_E | CW02 | 325 | CW02 | CW02 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_G | CW05 | 600 | CW05 | CW01 |
2020-03-15 | Product_G | CW01 | 482 | CW05 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_J | CW01 | 465 | CW01 | CW12 |
2020-03-15 | Product_J | CW12 | 323 | CW01 | CW12 |
我想比较每个 product
的两个 timestamps
的 plan_week
,并将它们排列在彼此下方,正如您在预期结果中看到的那样。
在 first_plan
列中,我想列出第一个时间戳的周数。
在 last_plan
列中,我想列出最后一个 teimestamp 的星期。
我目前正在使用此查询来获得 postgresSQL
中的结果:
SELECT
time_stamp,
product,
plan_week,
quantity,
(FIRST_VALUE(plan_week) OVER (PARTITION BY product ORDER BY time_stamp ASC)) first_plan,
(FIRST_VALUE(plan_week) OVER (PARTITION BY product ORDER BY time_stamp DESC)) last_plan
FROM operations;
但是,当我将此 sql 应用于 amazon-redshift
时,我得到:
ERROR: Aggregate window functions with an ORDER BY clause require a frame clause
我需要如何修改查询才能使其在 redshift 中也能正常工作?
手册解释了什么是框架条款:
- https://docs.aws.amazon.com/redshift/latest/dg/r_WF_first_value.html
- https://docs.aws.amazon.com/redshift/latest/dg/r_Window_function_synopsis.html
(window 应该向前或向后看多少行。)
您可能想要类似...
SELECT
time_stamp,
product,
plan_week,
quantity,
FIRST_VALUE(plan_week)
OVER (
PARTITION BY product
ORDER BY time_stamp
ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING
)
AS first_plan,
LAST_VALUE(plan_week)
OVER (
PARTITION BY product
ORDER BY time_stamp
ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING
)
AS last_plan
FROM
operations
注意,我使用 LAST_VALUE()
而不是反转 ORDER BY
。通常,最好为多个 window 函数保留相同的 window 子句。它使优化者的生活更轻松,这对您有好处。
CREATE TABLE operations (
id SERIAL PRIMARY KEY,
time_stamp DATE,
product VARCHAR,
plan_week VARCHAR,
quantity DECIMAL
);
INSERT INTO operations
(time_stamp, product, plan_week, quantity
)
VALUES
('2020-01-01', 'Product_A', 'CW01', '125'),
('2020-01-01', 'Product_B', 'CW01', '300'),
('2020-01-01', 'Product_C', 'CW08', '700'),
('2020-01-01', 'Product_D', 'CW01', '900'),
('2020-01-01', 'Product_G', 'CW05', '600'),
('2020-01-01', 'Product_J', 'CW01', '465'),
('2020-03-15', 'Product_A', 'CW01', '570'),
('2020-03-15', 'Product_C', 'CW02', '150'),
('2020-03-15', 'Product_E', 'CW02', '325'),
('2020-03-15', 'Product_G', 'CW01', '482'),
('2020-03-15', 'Product_J', 'CW12', '323');
预期结果:
time_stamp | product | plan_week | quantity | first_plan | last_plan |
---------- |-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_A | CW01 | 125 | CW01 | CW01 |
2020-03-15 | Product_A | CW01 | 570 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_B | CW01 | 300 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_C | CW08 | 700 | CW08 | CW02 |
2020-03-15 | Product_C | CW02 | 150 | CW08 | CW02 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_D | CW01 | 900 | CW01 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-03-15 | Product_E | CW02 | 325 | CW02 | CW02 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_G | CW05 | 600 | CW05 | CW01 |
2020-03-15 | Product_G | CW01 | 482 | CW05 | CW01 |
------------|-------------|--------------|------------|--------------|-------------|---
2020-01-01 | Product_J | CW01 | 465 | CW01 | CW12 |
2020-03-15 | Product_J | CW12 | 323 | CW01 | CW12 |
我想比较每个 product
的两个 timestamps
的 plan_week
,并将它们排列在彼此下方,正如您在预期结果中看到的那样。
在 first_plan
列中,我想列出第一个时间戳的周数。
在 last_plan
列中,我想列出最后一个 teimestamp 的星期。
我目前正在使用此查询来获得 postgresSQL
中的结果:
SELECT
time_stamp,
product,
plan_week,
quantity,
(FIRST_VALUE(plan_week) OVER (PARTITION BY product ORDER BY time_stamp ASC)) first_plan,
(FIRST_VALUE(plan_week) OVER (PARTITION BY product ORDER BY time_stamp DESC)) last_plan
FROM operations;
但是,当我将此 sql 应用于 amazon-redshift
时,我得到:
ERROR: Aggregate window functions with an ORDER BY clause require a frame clause
我需要如何修改查询才能使其在 redshift 中也能正常工作?
手册解释了什么是框架条款:
- https://docs.aws.amazon.com/redshift/latest/dg/r_WF_first_value.html
- https://docs.aws.amazon.com/redshift/latest/dg/r_Window_function_synopsis.html
(window 应该向前或向后看多少行。)
您可能想要类似...
SELECT
time_stamp,
product,
plan_week,
quantity,
FIRST_VALUE(plan_week)
OVER (
PARTITION BY product
ORDER BY time_stamp
ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING
)
AS first_plan,
LAST_VALUE(plan_week)
OVER (
PARTITION BY product
ORDER BY time_stamp
ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING
)
AS last_plan
FROM
operations
注意,我使用 LAST_VALUE()
而不是反转 ORDER BY
。通常,最好为多个 window 函数保留相同的 window 子句。它使优化者的生活更轻松,这对您有好处。