mysql 将行转置为列
Posted
技术标签:
【中文标题】mysql 将行转置为列【英文标题】:mysql trasnposing rows to columns 【发布时间】:2012-05-02 09:24:56 【问题描述】:我需要将以下查询输出为 csv。
我可以轻松编写 php 逻辑来将行从我的 group_concat 列转置为列
不过,我热衷于将尽可能多的数据部分保留在数据库中,并尽量减少 php 端的操作。
我正在尝试查询中 group_concat 下面的两列。
问题是 life_stage 列的丰度值也返回。如果除了操作 group_concat 键值之外没有其他办法,那很好,我只是想仔细检查一下。提前致谢
SELECT
`tr`.`tr_id_pk` as 'RecordKey',
`t`.`tax_name` as `TaxonName`,
`tr`.`tr_date` as 'Date',
`s`.`si_name` as 'SiteName',
`tr`.`tr_grid_reference` as 'GridReference',
`tr`.`tr_is_site_grid` as 'IsSiteGrid',
`r`.`rec_name` as 'Recorder',
`r`.`rec_email` as 'RecorderEmail',
`tr`.`tr_comment` as 'RecordComment',
`tr`.`tr_last_update` as 'LastUpdated',
`tr`.`tr_form_key` as 'FormKey',
`c`.`co_name` as 'County',
`vc`.`vc_name` as 'ViceCounty',
`h`.`hab_name` as 'Habitat',
GROUP_CONCAT(DISTINCT CONCAT_WS('=', `ra`.`ra_name`, `rad`.`rad_value`)) as 'RecordAttributeKeyValuePairs',
`rad`.`rad_value` AS `abundance`,
`rad`.`rad_value` AS `life_stage`
FROM
`taxon_record`as `tr`
INNER JOIN
`taxon`as `t` ON `tr`.`tax_id_fk` = `t`.`tax_id_pk`
INNER JOIN
`recorder`as `r` ON `tr`.`rec_id_fk` = `r`.`rec_id_pk`
INNER JOIN
`site`as `s` ON `tr`.`si_id_fk` = `s`.`si_id_pk`
LEFT JOIN
`county`as `c` ON `tr`.`co_id_fk` = `c`.`co_id_pk`
LEFT JOIN
`vice_county`as `vc` ON `tr`.`vc_id_fk` = `vc`.`vc_id_pk`
LEFT JOIN
`habitat`as `h` ON `tr`.`hab_id_fk` = `h`.`hab_id_pk`
LEFT JOIN
(`record_attribute_data`as `rad`
INNER JOIN `record_attribute`as `ra` ON (`rad`.`ra_id_fk` = `ra`.`ra_id_pk`)) ON (`tr`.`tr_id_pk` = `rad`.`tr_id_fk`)
WHERE
`r`.`rec_email` = 'some_email@somewhere.com'
GROUP BY `tr`.`tr_id_pk`;
【问题讨论】:
您应该确保问题显得响亮而清晰,而不是嵌入到一小段文字中。 感谢输入,我现在澄清了 每条记录是否具有完全相同数量的属性,具有相同的属性名称? 不幸的是,它是开放式的,所以有些可能有 3 个属性,有些可能有 5 个,依此类推。 【参考方案1】:您希望执行的操作称为“透视”您的数据,并且某些其他 RDBMS 具有本机支持,但 mysql 不支持(根据设计,因为开发人员认为此类操作属于表示层)。
但是,正如您所暗示的,您可以构建一个相当糟糕的 MySQL 查询来手动执行旋转操作(需要为每个输出列将属性表连接到查询一次):
SELECT tr.tr_id_pk, abundance, life_stage -- etc.
FROM taxon_record AS tr
LEFT JOIN (
SELECT rad.tr_id_fk, rad.rad_value AS abundance
FROM
record_attribute_data ra JOIN record_attribute rad
ON rad.ra_id_fk = ra.ra_id_pk
WHERE ra.ra_name = 'abundance'
) AS tAbundance ON tAbundance.tr_id_fk = tr.tr_id_pk
LEFT JOIN (
SELECT rad.tr_id_fk, rad.rad_value AS life_stage
FROM
record_attribute_data ra JOIN record_attribute rad
ON rad.ra_id_fk = ra.ra_id_pk
WHERE ra.ra_name = 'life_stage'
) AS tLife_Stage ON tLife_Stage.tr_id_fk = tr.tr_id_pk
-- etc.
如果您选择走这条路,您可以使用 PHP 中的循环构造或 MySQL 中的预准备语句生成此查询,从而使您的生活稍微轻松一些。
【讨论】:
是的,这是我正在考虑的方法,但我只是在检查它们是否是我设法错过的更简单的方法。反正我猜不是。感谢您的意见,我很感激。干杯。【参考方案2】:问题是您以不同的名称两次获取同一列吗?:
`rad`.`rad_value` AS `abundance`,
`rad`.`rad_value` AS `life_stage`
看起来你总是会得到同样的东西来丰富和 life_stage 那样。
【讨论】:
以上是关于mysql 将行转置为列的主要内容,如果未能解决你的问题,请参考以下文章