MySQL - 如何选择列以使结果成为树结构?

时间:2015-08-28 21:59:35

标签: mysql select split tree

如果我有一个包含以下快照的给定列

"A - B - 1"
"A - B - 2"
"A - C - 1"
"A - C - 2"
"X - B - 1"
"X - B - 2"
"X - C - 1"
"X - C - 2"

我应该选择哪个选择以便结果

"A",  "", ""
"", "B", ""
"",  "", "1"
"",  "", "2"
"", "C", ""
"",  "", "1"
"",  "", "2"
"X",  "", ""
"", "B", ""
"",  "", "1"
"",  "", "2"
"", "C", ""
"",  "", "1"
"",  "", "2"

有可能吗?

1 个答案:

答案 0 :(得分:1)

假设字符串中每个字符的位置是固定的,您可以使用字符串函数很容易地完成此操作。

select col1, col2, col3
from (  
  select distinct 
    substring(col1,1,1) col1, 
    null col2, 
    null col3, 
    substring(col1,1,1) ord 
  from t

  union all

  select distinct 
    null, 
    substring(col1,5,1), 
    null, 
    concat(substring(col1,1,1),substring(col1,5,1))
  from t

  union all

  select distinct 
    null, 
    null, 
    substring(col1,9,1),
    concat(substring(col1,1,1),substring(col1,5,1),substring(col1,9,1))
  from t  
) a order by ord;

Sample SQL Fiddle

此查询将返回:

|   col1 |   col2 |   col3 |
|--------|--------|--------|
|      A | (null) | (null) |
| (null) |      B | (null) |
| (null) | (null) |      1 |
| (null) | (null) |      2 |
| (null) |      C | (null) |
| (null) | (null) |      1 |
| (null) | (null) |      2 |
|      X | (null) | (null) |
| (null) |      B | (null) |
| (null) | (null) |      1 |
| (null) | (null) |      2 |
| (null) |      C | (null) |
| (null) | (null) |      1 |
| (null) | (null) |      2 |

<强>更新

如果你有一个固定长度的字符串,上面提供的答案是有效的 - 所有样本都考虑长度等于1的字符串。但是,如果需要可变长度字符串,请执行以下操作

SELECT col1, col2, col3
FROM (
  SELECT DISTINCT
    SUBSTRING_INDEX(col1, ' - ', 1) col1, 
    NULL col2, 
    NULL col3, 
    SUBSTRING_INDEX(col1, ' - ', 1) ord
  FROM t

  UNION ALL

  SELECT DISTINCT 
    NULL, 
    SUBSTRING_INDEX(SUBSTRING_INDEX(col1, ' - ', 2), ' - ', -1), 
    NULL, 
    CONCAT(SUBSTRING_INDEX(col1, ' - ', 1), SUBSTRING_INDEX(SUBSTRING_INDEX(col1, ' - ', 2), ' - ', -1)) ord
  FROM t

  UNION ALL

  SELECT DISTINCT
    NULL, 
    NULL,  
    SUBSTRING_INDEX(col1, ' - ', -1),
    CONCAT(SUBSTRING_INDEX(col1, ' - ', 1), SUBSTRING_INDEX(SUBSTRING_INDEX(col1, ' - ', 2), ' - ', -1), SUBSTRING_INDEX(col1, ' - ', -1)) ord
  FROM t
) a ORDER BY ord;