在尝试从MYSQL DB创建数据馈送时,我遇到了以下情况。在实际情况中涉及到更多的表,但我想保持这个简短,并集中在手头的问题上。我有两个带有中间表(products_options_values_to_products_options).的表(products_options_values,products_options)(对表格的格式表示歉意,但我认为您可以区分每个字段的值。)
TABLE: products_options_values<br>
products_options_values_id | products_options_values_name <br>
28 9-11<br>
52 Black<br>
53 In-Line<br>
TABLE: products_options_values_to_products_options<br>
products_options_values_to_products_options_id | products_options_id | products_options_values_id<br>
31 2 28<br>
56 1 52<br>
57 3 53<br>
TABLE: products_options<br>
products_options_id | products_options_name <br>
1 Color<br>
2 Size<br>
3 Style<br>
我正在尝试编写一条具有以下结果的SQL语句:来自不同表的关于某个产品的字段,字段名为products_options_name,并且在同一行中具有相应的products_options_values_name和相应值。例如:
Product_ID Product_Name MPN Price Color Size Style
00001 Acme Rollerskates A99 99.99 Black 9-11 In-Line
关于如何在MYSQL中实现这一结果,有什么帮助吗?感谢您的考虑和努力。标记
发布于 2013-01-06 23:17:41
要将您提供的表转换成这种格式,您基本上是在执行透视,但是MySQL没有透视函数。因此,您需要使用带有CASE
语句的聚合函数来复制它:
select
max(case when po.products_options_name = 'Color'
then pov.products_options_values_name else null end) Color,
max(case when po.products_options_name = 'Size'
then pov.products_options_values_name else null end) Size,
max(case when po.products_options_name = 'Style'
then pov.products_options_values_name else null end) Style
from products_options po
left join products_options_values_to_products_options pv
on po.products_options_id = pv.products_options_id
left join products_options_values pov
on pv.products_options_values_id = pov.products_options_values_id
请参阅SQL Fiddle with Demo
结果是:
| COLOR | SIZE | STYLE |
--------------------------
| Black | 9-11 | In-Line |
看起来您仍然需要加入包含产品详细信息的表中,如product_id
、product_name
、price
等。
我不能从您提供的表结构中看出您连接这些数据的位置,但是查询应该是这样的:
select p.product_id,
p.product_name,
p.MPN,
p.price,
max(case when po.products_options_name = 'Color'
then pov.products_options_values_name else null end) Color,
max(case when po.products_options_name = 'Size'
then pov.products_options_values_name else null end) Size,
max(case when po.products_options_name = 'Style'
then pov.products_options_values_name else null end) Style
from products p --- add join to the main products table
left join products_options po
on p.product_id = po.products_options_id
left join products_options_values_to_products_options pv
on po.products_options_id = pv.products_options_id
left join products_options_values pov
on pv.products_options_values_id = pov.products_options_values_id
group by p.product_id, p.product_name, p.MPN, p.price
发布于 2013-01-06 23:27:34
我不确定你是否听说过Magento,但这与他们的EAV设置类似。基本上,如果您希望将行转换为列,则必须为每个行值重复一次与字段值表的左连接。我将在下面做一个简化的版本。
products table:
[id, product_name]
1, product 1
2, product 2
3, product 3
product_fields table:
[id, product_id, field_name, field_value]
1, 1, color, red
2, 2, color, blue
3, 3, color, black
4, 1, size, XL
5, 2, size, XL
6, 3, size, XL
SELECT
p.product_name,
table1.field_value AS color,
table2.field_value AS size
FROM
products AS p LEFT JOIN product_fields AS table1 ON
p.id = table1.product_id AND
table1.field_name='color'
LEFT JOIN product_fields AS table2 ON
p.id = table2.product_id AND
table1.field_name='size'
通常,在join子句中将使用id而不是字段名,但您应该明白这一点。此外,sql server还提供了一个透视函数,它可能会执行您所需的操作。我不相信有Mysql的等价物,但你可以研究一下。
编辑:bluefeet的答案模拟了sql server的PIVOT函数。在2005年之前,sql server也是这样做的。他的答案是在我回答的时候贴出来的。
https://stackoverflow.com/questions/14183311
复制相似问题