sql数据库修改列名(SQL 行列转换 4 种方法,工作中 90% 场景都能用)

sql数据库修改列名(SQL 行列转换 4 种方法,工作中 90% 场景都能用)
SQL 行列转换 4 种方法,工作中 90% 场景都能用

做数据开发、ETL、数据分析的朋友,肯定绕不开「行列转换」—— 把行数据转成列,或列数据转成行。

今天一次性讲透 4 种常用方法,附完整代码,新手也能直接抄。

先定义一个测试表(大家先建表,方便跟着试):

-- 新建业务表:销售明细表

CREATE TABLE SALES

(

SNAME VARCHAR2(50),

SDATE DATE,

PRODUCT VARCHAR2(200),

AMOUNT NUMBER(12,2),

sql数据库修改列名(SQL 行列转换 4 种方法,工作中 90% 场景都能用)

AREA VARCHAR2(100)

)

-- 注释表与字段名称

COMMENT ON TABLE SALES IS '销售明细表';

COMMENT ON COLUMN SALES.SNAME IS '姓名';

COMMENT ON COLUMN SALES.SDATE IS '销售日期';

COMMENT ON COLUMN SALES.PRODUCT IS '销售产品';

COMMENT ON COLUMN SALES.AMOUNT IS '销售金额';

COMMENT ON COLUMN SALES.AREA IS '销售区域';

-- 插入测试数据

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('张三', TO_DATE('2026-01-01', 'YYYY-MM-DD'), '手机', 1299.59, '华北');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('李四', TO_DATE('2026-01-02', 'YYYY-MM-DD'), '电脑', 2792.36, '华东');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('王五', TO_DATE('2026-01-03', 'YYYY-MM-DD'), '平板', 3020.00, '华南');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('张三', TO_DATE('2026-01-06', 'YYYY-MM-DD'), '手机', 2679.50, '华北');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('李四', TO_DATE('2026-01-12', 'YYYY-MM-DD'), '电脑', 3629.02, '华东');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('王五', TO_DATE('2026-01-18', 'YYYY-MM-DD'), '平板', 2789.63, '华南');

COMMIT;

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('张三', TO_DATE('2026-02-16', 'YYYY-MM-DD'), '手机', 2027.90, '华北');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('李四', TO_DATE('2026-02-18', 'YYYY-MM-DD'), '电脑', 1169.12, '华东');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('王五', TO_DATE('2026-02-22', 'YYYY-MM-DD'), '平板', 1269.03, '华南');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('张三', TO_DATE('2026-02-20', 'YYYY-MM-DD'), '手机', 2873.32, '华北');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('李四', TO_DATE('2026-02-22', 'YYYY-MM-DD'), '电脑', 3269.07, '华东');

INSERT INTO SALES (SNAME, SDATE, PRODUCT, AMOUNT, AREA) VALUES ('王五', TO_DATE('2026-02-23', 'YYYY-MM-DD'), '平板', 3369.03, '华南');

COMMIT;

一、行转列(最常用)

方法 1:CASE WHEN(通用所有数据库,新手首选)

-- 行转列:按员工分组,展示各月销售额

SELECT

SNAME AS "员工姓名",

SUM(CASE WHEN TO_CHAR(SDATE,'YYYYMM')='202601' THEN AMOUNT ELSE 0 END) AS "2026年1月",

SUM(CASE WHEN TO_CHAR(SDATE,'YYYYMM')='202602' THEN AMOUNT ELSE 0 END) AS "2026年2月"

FROM SALES

GROUP BY SNAME;

优点:兼容 MySQL、Oracle、SQL Server,无版本限制

缺点:列固定,新增月份需扩展代码

方法 2:PIVOT(SQL Server/Oracle 专用,简洁)

-- Oracle 行转列

WITH SALES_BASE AS

(

SELECT SNAME

,TO_CHAR(SDATE,'YYYYMM') AS SMONTH

,AMOUNT

FROM SALES

)

SELECT SNAME AS "员工姓名"

,"2026年1月"

,"2026年2月"

FROM SALES_BASE

PIVOT (

SUM(AMOUNT)

FOR SMONTH IN (

'202601' AS "2026年1月",

'202602' AS "2026年2月"

)

);

优点:代码简洁,适合固定列转换

缺点:仅支持部分数据库

二、列转行

方法 3:UNION ALL(通用所有数据库)

列转回行(以上面方法1行转列结果为基表):

WITH SALES_BASE AS

(

SELECT

SNAME AS "员工姓名",

SUM(CASE WHEN TO_CHAR(SDATE,'YYYYMM')='202601' THEN AMOUNT ELSE 0 END) AS "2026年1月销售额",

SUM(CASE WHEN TO_CHAR(SDATE,'YYYYMM')='202602' THEN AMOUNT ELSE 0 END) AS "2026年2月销售额"

FROM SALES

GROUP BY SNAME

)

-- 列转行

SELECT 员工姓名

,'2026年1月' AS 月份

,"2026年1月销售额" AS 销售额

FROM SALES_BASE

UNION ALL

SELECT 员工姓名

,'2026年2月' AS 月份

,"2026年2月销售额" AS 销售额

FROM SALES_BASE;

优点:通用、逻辑简单,新手易理解

缺点:扩展时代码也多

方法 4:UNPIVOT(SQL Server/Oracle 专用)

列转回行(以上面方法2行转列结果为中间表):

WITH SALES_BASE AS

(

SELECT SNAME

,TO_CHAR(SDATE,'YYYYMM') AS SMONTH

,AMOUNT

FROM SALES

)

,SALES_PIVOT AS

(

SELECT SNAME AS "员工姓名"

,"2026年1月销售额"

,"2026年2月销售额"

FROM SALES_BASE

PIVOT (

SUM(AMOUNT)

FOR SMONTH IN (

'202601' AS "2026年1月销售额",

'202602' AS "2026年2月销售额"

)

)

)

SELECT 员工姓名

,SMONTH AS "年月"

,AMOUNT AS "销售额"

FROM SALES_PIVOT

UNPIVOT (

AMOUNT FOR SMONTH IN (

"2026年1月销售额" AS '202601'

,"2026年2月销售额" AS '202602'

)

)

优点:代码短,适合批量列转行

缺点:仅支持部分数据库

总结:

新手优先用 CASE WHEN / UNION ALL:通用所有数据库,不会踩版本坑;

SQL Server/Oracle 可用 PIVOT/ UNPIVOT:简化代码,效率更高;

行转列关键:GROUP BY 分组 + 条件判断;列转行关键:UNION ALL 合并结果。

文章版权声明:除非注明,否则均为边学边练网络文章,版权归原作者所有