Mysql Crosstab验证存在

时间:2013-08-28 04:09:17

标签: mysql sql reporting

我是stackoverflow中的新手,我有一些问题试图做subj。报告。

表示例

Group  Client   Atribute
Group1 Client1  Atribute1
Group1 Client1  Atribute1
Group1 Client2  Atribute2
Group2 Client3  Atribute1
Group3 Client4  Atribute2
Group3 Client5  Atribute2
Group3 Client5  Atribute2
Group3 Client6  Atribute3

注意:客户端和组列将在此示例中重复。

需要的报告

Group  Client Atribute1 Atribute2 Atribute3 
Group1 Client1  Yes         no       no 
Group1 Client2  no          yes      no 
Group2 Client3  yes         no       no 
Group3 Client4  no          yes      no 
Group3 Client5  no          yes      no 
Group3 Client6  no          no       yes 

主要的复杂因素是我们需要客户验证客户是否有不同的属性。

我一开始就陷入困境,我想到这样的事情:

SELECT
 group,
 client,
 CASE WHEN EXISTS
 (SELECT client FROM table
  WHERE client IN ( SELECT client FROM table
  WHERE Atribute = 3 ) -- The problem is that since there is an attribute for one of the    clients the subquery result true and will go to the "THEN" dor all the clients.
 ) THEN 'Yes' ELSE 'No' END AS Atribute3,
FROM
 table
GROUP BY group, client

任何帮助将不胜感激。请原谅我的英文!最好的问题。

1 个答案:

答案 0 :(得分:0)

你可以用动态SQL

这样做
SET @sql = NULL;

SELECT GROUP_CONCAT(DISTINCT
         CONCAT('MAX(CASE WHEN atribute = ''',
                atribute,
                ''' THEN ''yes'' ELSE ''no'' END) ',
                atribute))
  INTO @sql
  FROM table1;

SET @sql = CONCAT('SELECT `group`, client, ', @sql, ' 
                   FROM table1 
                   GROUP BY `group`, client');

PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;

输出:

|  GROUP |  CLIENT | ATRIBUTE1 | ATRIBUTE2 | ATRIBUTE3 |
|--------|---------|-----------|-----------|-----------|
| Group1 | Client1 |       yes |        no |        no |
| Group1 | Client2 |        no |       yes |        no |
| Group2 | Client3 |       yes |        no |        no |
| Group3 | Client4 |        no |       yes |        no |
| Group3 | Client5 |        no |       yes |        no |
| Group3 | Client6 |        no |        no |       yes |

这是 SQLFiddle 演示

为简化调用端的操作,您可以将其包装到存储过程

DELIMITER $$
CREATE PROCEDURE sp_report()
BEGIN
  SET @sql = NULL;

  SELECT GROUP_CONCAT(DISTINCT
           CONCAT('MAX(CASE WHEN atribute = ''',
                  atribute,
                  ''' THEN ''yes'' ELSE ''no'' END) ',
                  atribute))
    INTO @sql
    FROM table1;

  SET @sql = CONCAT('SELECT `group`, client, ', @sql, ' 
                     FROM table1 
                     GROUP BY `group`, client');

  PREPARE stmt FROM @sql;
  EXECUTE stmt;
  DEALLOCATE PREPARE stmt;
END$$
DELIMITER ;

然后像

一样使用它
CALL sp_report();

这是 SQLFiddle 演示