Sql组合从单个表到单个表

рüф*_*ффп 9 mysql sql

我有一个看起来像这样的表:

表提取物

    Owner   | Attribute | value
----------------------------------------------------
    10      | COLOR     | BLUE
    10      | COLOR     | RED
    10      | COLOR     | GREEN
    10      | SIZE      | BIG
    20      | COLOR     | GREEN
    20      | SIZE      | MEDIUM
    20      | MEMORY    | 16G
    20      | MEMORY    | 32G
    30      | COLOR     | RED
    30      | COLOR     | BLUE
    30      | MEMORY    | 64G
Run Code Online (Sandbox Code Playgroud)

是否有一个SQL将使用单个索引计算所有属性的组合(结果中的最后一列):

Owner   | Attribute | Value | Rule_No
10      | COLOR     | BLUE  | 1
10      | SIZE      | BIG   | 1
10      | COLOR     | RED   | 2
10      | SIZE      | BIG   | 2
10      | COLOR     | GREEN | 3
10      | SIZE      | BIG   | 3
20      | COLOR     | GREEN | 1
20      | SIZE      | MEDIUM| 1
20      | MEMORY    | 16G   | 1
20      | COLOR     | GREEN | 2
20      | SIZE      | MEDIUM| 2
20      | MEMORY    | 32G   | 2
30      | COLOR     | BLUE  | 1
30      | MEMORY    | 64G   | 1
30      | COLOR     | RED   | 2
30      | MEMORY    | 64G   | 2
Run Code Online (Sandbox Code Playgroud)

规则编号对于每个所有者是唯一的(所有者'10'的规则'1'与所有者'20'的规则'1'无关.

我试图使用SQL交叉连接,但属性的数量不固定,然后我不能使用它(每个属性需要一个交叉连接),我希望组合是新行而不是新列.

我试图用Talend Open Studio - Data Integration它做,但只使用SQL的解决方案对我来说会更好.

egg*_*yal 6

真的想要问题中给出的形式的数据(这需要进一步聚合Rule_No在大多数情况下是有用的),还是你最终想要转移它?也就是说,规则连接在一起(每个属性成为自己的列),如下所示:

+---------+-------+-------+--------+--------+
| Rule_No | Owner | COLOR | SIZE   | MEMORY |
+---------+-------+-------+--------+--------+
|       1 |    10 | BLUE  | BIG    | NULL   |
|       2 |    10 | RED   | BIG    | NULL   |
|       3 |    10 | GREEN | BIG    | NULL   |
|       1 |    20 | GREEN | MEDIUM | 16G    |
|       2 |    20 | GREEN | MEDIUM | 32G    |
|       1 |    30 | RED   | NULL   | 64G    |
|       2 |    30 | BLUE  | NULL   | 64G    |
+---------+-------+-------+--------+--------+

可以使用以下查询来转动此类数据:

SELECT   @t:=IF(Owner=@o,@t,0)+1 AS Rule_No,
         @o:=Owner AS Owner,
         `COLOR`,`SIZE`,`MEMORY`
FROM     (SELECT DISTINCT Owner, @t:=0 FROM my_table) t0

  LEFT JOIN (
    SELECT Owner, value AS `COLOR`
    FROM   my_table
    WHERE  Attribute='COLOR'
  ) AS `t_COLOR` USING (Owner)

  LEFT JOIN (
    SELECT Owner, value AS `SIZE`
    FROM   my_table
    WHERE  Attribute='SIZE'
  ) AS `t_SIZE` USING (Owner)

  LEFT JOIN (
    SELECT Owner, value AS `MEMORY`
    FROM   my_table
    WHERE  Attribute='MEMORY'
  ) AS `t_MEMORY` USING (Owner)

ORDER BY Owner, Rule_No
Run Code Online (Sandbox Code Playgroud)

由于属性列表是动态的,因此可以使用查询来构造上述SQL,从中准备并执行语句:

SELECT CONCAT('
         SELECT   @t:=IF(Owner=@o,@t,0)+1 AS Rule_No,
                  @o:=Owner AS Owner,
                  ', GROUP_CONCAT(DISTINCT CONCAT(
                    '`',REPLACE(Attribute,'`','``'),'`'
                  )), '
         FROM     (SELECT DISTINCT Owner, @t:=0 FROM my_table) t0
       ', GROUP_CONCAT(DISTINCT CONCAT('
           LEFT JOIN (
             SELECT Owner, value AS `',REPLACE(Attribute,'`','``'),'`
             FROM   my_table
             WHERE  Attribute=',QUOTE(Attribute),'
           ) AS `t_',REPLACE(Attribute,'`','``'),'` USING (Owner)
         ') SEPARATOR ''), '
         ORDER BY Owner, Rule_No
       ') INTO @sql
FROM   my_table;

PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;
Run Code Online (Sandbox Code Playgroud)

sqlfiddle上看到它.