【mysql】逗號分割字段的行列轉換
阿新 • • 發佈:2017-12-29
lec mysql 由於 int creat prim sql語句 post 之前
由於很多業務表因為歷史原因或者性能原因,都使用了違反第一範式的設計模式,即同一個列中存儲了多個屬性值。這種模式下,應用常常需要將這個列依據分隔符進行分割,並得到列轉行的結果:
建表語句:
1 DROP table if EXISTS tbl_name; 2 CREATE TABLE tbl_name( 3 id int(11) not null auto_increment, 4 userName varchar(100) not null, 5 PRIMARY KEY(id) 6 ) 7 ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8; 8 9 insert into tbl_name values (1,‘a,aa,aaa‘); 10 insert into tbl_name values (2,‘b,bb‘); 11 insert into tbl_name values (3,‘c,cc‘);
如下圖:
sql語句:
1 SELECT a.id,SUBSTRING_INDEX(SUBSTRING_INDEX(a.userName,‘,‘,b.help_topic_id+1),‘,‘,-1) as name 2 from tbl_name a left joinmysql.help_topic b 3 on b.help_topic_id < (LENGTH(a.userName)-LENGTH(REPLACE(a.userName,‘,‘,‘‘))+1) 4 ORDER BY a.id;
執行結果:
分析如下:
LENGTH(a.userName)-LENGTH(REPLACE(a.userName,‘,‘,‘‘))+1
表示了按逗號分割後,獲得行轉成列的數量,以下簡稱n;
根據id進行循環 { 判斷:i 是否 <= n { 獲取最靠近第 i 個逗號之前的數據, 即 SUBSTRING_INDEX(SUBSTRING_INDEX(a.userName,‘,‘,b.help_topic_id+1),‘,‘,-1) i = i +1 } id = id +1 }
總結:
這種方法的缺點在於,我們需要一個擁有連續數列的獨立表(這裏是incre_table)。並且連續數列的最大值一定要大於符合分割的值的個數。當然,mysql內部也有現成的連續數列表可用。如mysql.help_topic: help_topic_id 共有504個數值,一般能滿足於大部分需求了。
【mysql】逗號分割字段的行列轉換