【问题标题】:MySQL count() problemMySQL count() 问题
【发布时间】:2009-09-30 15:52:22
【问题描述】:

设置:

create table main(id integer unsigned);
create table test1(id integer unsigned);
create table test2(id integer unsigned);

insert into main(id) value(1);
insert into test1(id) value(1);
insert into test1(id) value(1);
insert into test2(id) value(1);    
insert into test2(id) value(1);
insert into test2(id) value(1);

使用:

   select main.id, 
          count(test1.id),
          count(test2.id) 
     from main
left join test1 on main.id=test1.id
left join test2 on main.id=test2.id
group by main.id;

...返回:

+------+-----------------+-----------------+
| id   | count(test1.id) | count(test2.id) |
+------+-----------------+-----------------+
|    1 |               6 |               6 |
+------+-----------------+-----------------+

如何得到 1 2 3 的期望结果?

编辑

解决方案应该是可扩展的,我以后要查询main.id的多个count()信息。

【问题讨论】:

    标签: sql mysql count


    【解决方案1】:

    不是最佳的,但有效:

    select 
        count(*),
        (select count(*) from test1 where test1.id = main.id) as test1_count,
        (select count(*) from test2 where test2.id = main.id) as test2_count
    from main
    

    【讨论】:

    • 不,子查询不是我想要的。
    • @Mask:为什么不是你想要的?它给出了你说你想要的答案。如果您有其他要求,则需要说明。
    【解决方案2】:

    您创建的表包含以下内容:

    主表

    id
    ----
    1
    

    表测试1

    id
    ----
    1
    1
    

    表测试2

    id
    ----
    1
    1
    1
    

    当你像你一样加入这个时,你会得到以下内容

    id  id  id 
    -----------
    1   1   1
    1   1   1
    1   1   1
    1   1   1
    1   1   1
    1   1   1
    

    那么 SQL 应该如何做出不同的回答呢?

    您可以致电:

    SELECT id,COUNT(id) FROM main GROUP BY id
    

    对于每个表,然后通过 id 加入它们。

    【讨论】:

      【解决方案3】:

      不确定这在 MySQL 中是否完全按照所写的方式工作(我使用的是 Oracle):

        1  select main.id, t1.rowcount, t2.rowcount
        2  from main
        3    left join (select id,count(*) rowcount from test1 group by id) t1
        4              on t1.id = main.id
        5    left join (select id,count(*) rowcount from test2 group by id) t2
        6*             on t2.id = main.id
      

      SQL> /

          ID   ROWCOUNT   ROWCOUNT
      

           1          2          3
      

      【讨论】:

        【解决方案4】:

        您无意中在 test1 和 test2 之间创建了笛卡尔积,因此 test1 中的每个匹配行都与 test2 中的每个匹配行相结合。因此,这两个计数的结果是 test1 中的匹配行数乘以 test2 中的匹配行数。

        这是一种常见的 SQL 反模式。很多人都有这个问题,因为他们认为他们必须在一个查询中获得两个计数。

        此线程上的其他一些人提出了通过创造性地使用子查询来补偿笛卡尔积的方法,但解决方案只是运行两个单独的查询:

        select main.id, count(test1.id)
        from main
        left join test1 on main.id=test1.id
        group by main.id;
        
        select main.id, count(test2.id) 
        from main
        left join test2 on main.id=test2.id
        group by main.id;
        

        您不必在单个 SQL 查询中完成所有任务!通常,编写多个更简单的查询更容易编写代码——RDBMS 也更容易执行。

        【讨论】:

          【解决方案5】:

          您可以使用以下方法获得所需的结果:

          SELECT COUNT(*) as main_count, 
          (SELECT COUNT(*) FROM table1) as table1Count,
          (SELECT COUNT(*) from table2) as table2Count FROM main
          

          【讨论】:

            猜你喜欢
            • 2013-02-06
            • 1970-01-01
            • 2021-01-30
            • 2023-03-26
            • 1970-01-01
            • 2013-04-21
            • 1970-01-01
            • 2019-11-20
            • 2016-11-18
            相关资源
            最近更新 更多