查询动态列表时GROUP_CONCAT中的COUNT不起作用

问题描述

我有一个名为table1的表,如下所示:

   id    period         value       name
   1     2020-06-01     3           anna
   2     2020-06-01     2           anna
   3     2020-06-01     3           anna
   4     2020-06-01     1           juned
   5     2020-06-01     3           juned
   6     2020-06-01     2           juned
   7     2020-07-01     3           anna
   8     2020-07-01     2           anna
   9     2020-07-01     2           anna
  10     2020-07-01     3           juned
  11     2020-07-01     3           juned
  12     2020-07-01     3           juned

我希望查询结果显示3的计数

name      2020-06-01     2020-07-01
anna          2              2
juned         1              3

我尝试过这是代码,但是它导致错误#1111 - invalid use of group function

SET @sql = NULL;
SELECT
    GROUP_CONCAT(disTINCT
        CONCAT(
            'MAX(IF (table1.period = "',table1.period,'",COUNT(CASE WHEN value = 3 THEN 1 END),0)) AS `','`'
        )
    ) INTO @sql
FROM table1;
SET @sql =  CONCAT(
                'SELECT name,',@sql,' FROM table1 GROUP BY name'
            ); 
PREPARE stmt FROM @sql;
EXECUTE stmt;

解决方法

我将动态SQL编写为:

SET @sql = NULL;
SELECT GROUP_CONCAT(DISTINCT 'SUM(value = 3 AND period = ''',period,''') AS `','`')
INTO @sql
FROM table1;

SET @sql =  CONCAT('SELECT name,',@sql,' FROM table1 GROUP BY name'); 
          
-- debug
select @sql;

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

代码的主要问题是在聚合函数中对条件表达式进行措辞的方式。另外:

  • 您不需要在CONCAT()中使用GROUP_CONCAT():您可以在GROUP_CONCAT()中放置多个值,并用字符串分隔

  • 对文字字符串使用单引号而不是双引号

  • 一旦查询执行,
  • DEALLOCATE语句处理程序

Demo on DB Fiddle -归功于Meet Soni首先创造了小提琴。

生成的sql:

| @sql                                                                                                                                                     |
| :------------------------------------------------------------------------------------------------------------------------------------------------------- |
| SELECT name,SUM(value = 3 AND period = '2020-06-01') AS `2020-06-01`,SUM(value = 3 AND period = '2020-07-01') AS `2020-07-01` FROM table1 GROUP BY name |

查询结果:

name  | 2020-06-01 | 2020-07-01
:---- | ---------: | ---------:
anna  |          2 |          1
juned |          1 |          3