2014-03-06 60 views
1

我有一个表具有不同的行,每行有相同项目的不同键。我想创建一个mySQL查询,将不同的键作为列放入一个新表中。 原始表:有多个键的表的mySQL查询

id locale key   value 
1 en description Great trip around cordoba's jklfjklfsjfdsk sdjk ds... 
1 en highlights_1 horse back riding 
1 en highlights_2 Asado 
1 en highlights_3 Free drinks 

要求的结果:

id description  highlights_1  highlights_2  highlights_3 ... 
1 Great trip ar... horse back riding Asado    Free drinks 

我所做的查询(并让我只需一个键/列的新表...)

SELECT activity.id, 
    activity_multilingual_fields_text.value AS activitydescription 
    FROM activity 
    LEFT JOIN activity_multilingual_fields_text ON activity_multilingual_fields_text.id = activity.id AND activity_multilingual_fields_text.locale = "en" 
GROUP BY activity.id 

我会感谢您的帮助!

+1

W8ing一些好的灵魂格式化这个问题。 – Guerra

+0

这被称为“数据透视查询”。你知道key的可能值的确切数量,还是动态的?如果是动态的,则必须在应用程序代码或存储过程中创建动态SQL语句。无论哪种方式,在这里解决这个问题都有很多答案。 –

+0

@Milen Pavlov感谢您的编辑......不知道这里的风格,我试图添加图片,但还没有足够的声望点:-( – JNewbie

回答

1

这最终并不困难,因为key的固定和有限数量的可能值。您不需要动态构建SQL,它可以是硬编码的。

一般模式是包含CASE语句,如果key的值与预定义的字符串匹配,则返回value列。这需要为每个可能的key完成。

这会导致5个单独的行,但大多数为NULL。那么你将每个CASE包装在一个MAX()集合中,这些集合会丢弃NULL并将每个折叠为单个行。 A GROUP BY必须应用于所选的其他列。

SELECT 
    activity.id, 
    MAX(CASE WHEN lf.`key` = 'description' THEN lf.value ELSE NULL END) AS `description`, 
    MAX(CASE WHEN lf.`key` = 'highlights_1' THEN lf.value ELSE NULL END) AS `highlights_1`, 
    MAX(CASE WHEN lf.`key` = 'highlights_2' THEN lf.value ELSE NULL END) AS `highlights_2`, 
    MAX(CASE WHEN lf.`key` = 'highlights_3' THEN lf.value ELSE NULL END) AS `highlights_3`, 
    MAX(CASE WHEN lf.`key` = 'highlights_4' THEN lf.value ELSE NULL END) AS `highlights_4` 
FROM 
    activity 
    LEFT JOIN activity_multilingual_fields_text lf 
    ON lf.id = activity.id 
     AND lf.locale = "en" 
GROUP BY activity.id 

这里有一个演示:http://sqlfiddle.com/#!2/bc028/3

+0

谢谢!这个伎俩。对我这样的新手小澄清,因为它带我一分钟了解 - 将“lf”更改为表的名称... – JNewbie

+0

@JNewbie是的,我最初在'FROM'子句中省略了'lf'的别名,但后来添加它,它只是一个别名尽管为了节省重复'activity_multilingual_fields_text'的数量。在这种情况下,实际上可以省略两者,因为您没有其他名为“value”的列。 –

0

GROUP BY activity.id将把结果聚合成id列中每个唯一值的1个结果记录。这可能就是为什么到目前为止,你的代码只能得到新表中的一个键/列。除此之外,这个例子似乎并不完整。你在哪里创建桌子?那是你正在用你用来执行查询的任何服务器端语言做的事情吗?

+0

嗨,谢谢你的回答!我已经尝试过没有GROUP BY,它给了我5行(作为键)为每个活动id,我想要的密钥列。我在phpMyAdmin上使用这个查询,我想创建表并导出它。 – JNewbie