创建一个视图,其中包含来自六个不同记录的每一行数据[PostgreSQL]
Create a view that contains in every row data that comes from six different records[PostgreSQL]
我有一个包含加油站价格的 table。每个加油站都有六个不同燃料类型(柴油、普通、超级)和服务类型(汽车服务、全面服务)的价格记录。例如,我在 table "gas_station_prices"
中有 "id_gas_station" = 155 的加油站价格记录
id_price|price_gas_station|id_gas_station|id_fuel_type|id_service_type
3041 |2.29 |155 |2 |1
2631 |2.52 |155 |1 |1
3861 |2.43 |155 |1 |2
4681 |1.84 |155 |3 |2
3451 |1.93 |155 |3 |1
4271 |2.2 |155 |2 |2
我有两个包含燃料类型和服务类型的目录
fuel_type目录:
id_fuel_type |name_fuel_type
1 |SUPER
2 |REGULAR
3 |DIESEL
service_type目录:
id_service_type |name_service_type
1 |FULL SERVICE
2 |AUTO SERVICE
我需要创建一个 SQL 视图,其中包含列 "price_gas_station" 的六个记录价格的并集,每个 gas_station 如下所示:
id_gas_station|fs_sup_p |fs_reg_p |fs_die_p |as_sup_p |as_reg_p|as_die_p|
155 |2.52 |2.29 |1.93 |2.43 |2.2 |1.84
您可以使用条件聚合:
SELECT id_gas_station,
MAX(CASE WHEN id_fuel_type = 1 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_sup_p,
MAX(CASE WHEN id_fuel_type = 2 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_reg_p,
MAX(CASE WHEN id_fuel_type = 3 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_die_p,
... etc
FROM mytable
GROUP BY id_gas_station
这是使用 CROSSTAB 的另一种方法 (http://www.postgresql.org/docs/current/static/tablefunc.html)
SELECT *
FROM crosstab(
'
SELECT
gsp.id_gas_station,
LOWER(LEFT(st.name_service_type,4) || ft.name_fuel_type) AS price_type,
gsp.price_gas_station
FROM
gas_station_prices gsp
JOIN
fuel_type ft
ON (ft.id_fuel_type = gsp.id_fuel_type)
JOIN
service_type st
ON (st.id_service_type = gsp.id_service_type)
ORDER BY
1,2
'
) AS ct (
id_gas_station INT,
auto_diesel FLOAT,
auto_regular FLOAT,
auto_super FLOAT,
full_diesel FLOAT,
full_regular FLOAT,
full_super FLOAT
);
Giorgos 解决方案应该同样好 - 或许也更具可读性?在大多数情况下,这是一个偏好问题。我只是想向您展示一个替代方案。
我有一个包含加油站价格的 table。每个加油站都有六个不同燃料类型(柴油、普通、超级)和服务类型(汽车服务、全面服务)的价格记录。例如,我在 table "gas_station_prices"
中有 "id_gas_station" = 155 的加油站价格记录id_price|price_gas_station|id_gas_station|id_fuel_type|id_service_type
3041 |2.29 |155 |2 |1
2631 |2.52 |155 |1 |1
3861 |2.43 |155 |1 |2
4681 |1.84 |155 |3 |2
3451 |1.93 |155 |3 |1
4271 |2.2 |155 |2 |2
我有两个包含燃料类型和服务类型的目录
fuel_type目录:
id_fuel_type |name_fuel_type
1 |SUPER
2 |REGULAR
3 |DIESEL
service_type目录:
id_service_type |name_service_type
1 |FULL SERVICE
2 |AUTO SERVICE
我需要创建一个 SQL 视图,其中包含列 "price_gas_station" 的六个记录价格的并集,每个 gas_station 如下所示:
id_gas_station|fs_sup_p |fs_reg_p |fs_die_p |as_sup_p |as_reg_p|as_die_p|
155 |2.52 |2.29 |1.93 |2.43 |2.2 |1.84
您可以使用条件聚合:
SELECT id_gas_station,
MAX(CASE WHEN id_fuel_type = 1 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_sup_p,
MAX(CASE WHEN id_fuel_type = 2 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_reg_p,
MAX(CASE WHEN id_fuel_type = 3 AND
id_service_type = 1
THEN price_gas_station
END) AS fs_die_p,
... etc
FROM mytable
GROUP BY id_gas_station
这是使用 CROSSTAB 的另一种方法 (http://www.postgresql.org/docs/current/static/tablefunc.html)
SELECT *
FROM crosstab(
'
SELECT
gsp.id_gas_station,
LOWER(LEFT(st.name_service_type,4) || ft.name_fuel_type) AS price_type,
gsp.price_gas_station
FROM
gas_station_prices gsp
JOIN
fuel_type ft
ON (ft.id_fuel_type = gsp.id_fuel_type)
JOIN
service_type st
ON (st.id_service_type = gsp.id_service_type)
ORDER BY
1,2
'
) AS ct (
id_gas_station INT,
auto_diesel FLOAT,
auto_regular FLOAT,
auto_super FLOAT,
full_diesel FLOAT,
full_regular FLOAT,
full_super FLOAT
);
Giorgos 解决方案应该同样好 - 或许也更具可读性?在大多数情况下,这是一个偏好问题。我只是想向您展示一个替代方案。