如何在MySQL中将行式数据转换为列式数据?
行转列实现方案
需求说明
原始查询结果(行式存储):
| rollNo | subject | score |
|---|---|---|
| 1 | 数学 | 90 |
| 1 | 英语 | 80 |
| 1 | 科学 | 70 |
| 1 | 计算机 | 90 |
期望输出(列式存储):
| rollNo | 数学 | 英语 | 科学 | 计算机 |
|---|---|---|---|---|
| 1 | 90 | 80 | 70 | 90 |
具体实现方法
方法1:CASE WHEN 通用写法(适配多数数据库)
如果科目是固定值,可以直接用CASE语句硬编码实现:
SELECT rollNo, MAX(CASE WHEN subject = '数学' THEN score END) AS 数学, MAX(CASE WHEN subject = '英语' THEN score END) AS 英语, MAX(CASE WHEN subject = '科学' THEN score END) AS 科学, MAX(CASE WHEN subject = '计算机' THEN score END) AS 计算机 FROM 你的表名 GROUP BY rollNo;
方法2:数据库内置PIVOT函数(如SQL Server、Oracle)
以SQL Server为例,利用PIVOT函数快速转置:
SELECT rollNo, 数学, 英语, 科学, 计算机 FROM (SELECT rollNo, subject, score FROM 你的表名) AS 源表 PIVOT (MAX(score) FOR subject IN (数学, 英语, 科学, 计算机)) AS 转置表;
方法3:动态SQL(应对科目不固定的情况,以MySQL为例)
如果科目数量或名称不固定,可通过动态生成SQL语句实现:
SET @sql = NULL; SELECT GROUP_CONCAT(DISTINCT CONCAT( 'MAX(CASE WHEN subject = ''', subject, ''' THEN score END) AS ', subject ) ) INTO @sql FROM 你的表名; SET @sql = CONCAT('SELECT rollNo, ', @sql, ' FROM 你的表名 GROUP BY rollNo'); PREPARE stmt FROM @sql; EXECUTE stmt; DEALLOCATE PREPARE stmt;
内容的提问来源于stack exchange,提问作者Pradip
相关产品推荐
相关产品推荐

