简体   繁体   English

在案例表达的条件部分内使用计数功能

[英]Use Count function inside conditional part of Case Expression

I have two tables with the following sample records in oracle database 我在Oracle数据库中有两个带有以下示例记录的表

1. staffs 1.员工

inst_name   name    sid
ABC         John    1
PQR         Sam     2
ABC         Tom     3
ABC         Amit    4
PQR         Jack    5

2. staffaccounts 2.人员账户

sid     account_no
1       4587
1       4588
2       4589
3       4581
3       4582
5       4583
5       4585
4       4586

Where I want the result like 我想要的结果像

inst_name   account_type    total
PQR         SINGLE          1
ABC         SINGLE          1
PQR         DOUBLE          1
ABC         DOUBLE          2

This can be achieved by a outer query, but I want to write a query where there is no outer query. 这可以通过外部查询来实现,但是我想编写一个没有外部查询的查询。 Want to accomplish it in one single query. 想要在一个查询中完成。

SELECT
    A .inst_name,
    (
        CASE COUNT (b.ac_no)
        WHEN 1 THEN
            'Single'
        WHEN 2 THEN
            'Double'
        END
    ) account_type,
    COUNT (A . NAME)
FROM
    staffs A,
    staffaccounts b
WHERE
    A . s_id = b.s_id
GROUP BY
    A .inst_name

The above query gives error ORA-00907: missing right parenthesis . 上面的查询给出错误ORA-00907: missing right parenthesis Can it be done in single query or is outer query the only way out. 可以在单个查询中完成还是外部查询是唯一的出路。

Oracle Version is 10g 

May be something like this would work. 可能像这样会起作用。

SELECT
    A.inst_name,
        CASE COUNT (b.account_no)
        WHEN 1 THEN
            'Single'
        WHEN 2 THEN
            'Double'
        END account_type,
    COUNT (A.name)
FROM
    staffs A JOIN
    staffaccounts b
ON
    A.SID = b.sid
GROUP BY
    A.inst_name , a.sid
    ORDER BY 3;  

You should learn how to properly use JOIN syntax. 您应该学习如何正确使用JOIN语法。 I prefer the explicit comparison syntax for CASE . 我更喜欢CASE的显式比较语法。

This may be what you want: 这可能是您想要的:

SELECT s.inst_name,
       (CASE WHEN COUNT(sa.ac_no) = 1 THEN 'Single'
             WHEN COUNT(sa.ac_no) = 2 THEN 'Double'
        END) as account_type,
       COUNT(*)
FROM staffs s JOIN
     staffaccounts sa
     ON s.SID = sa.sid
GROUP BY s.inst_name;

EDIT: 编辑:

Now I see what you want: 现在我明白了你想要什么:

SELECT s.inst_name,
       (CASE WHEN cnt = 1 THEN 'Single'
             WHEN cnt = 2 THEN 'Double'
        END) as account_type,
       COUNT(*)
FROM (SELECT s.*, COUNT(*) as cnt
      FROM staffs s JOIN
           staffaccounts sa
           ON s.SID = sa.sid
      GROUP BY s.id
     ) s
GROUP BY s.inst_name,
         (CASE WHEN cnt = 1 THEN 'Single'
               WHEN cnt = 2 THEN 'Double'
          END);

You are grouping by inst_name , but this is not what you actually want, because you don't want a result row per inst_name , but per inst_name and account_type . 您正在按inst_name分组,但这并不是您真正想要的,因为您不希望每个inst_name而是每个inst_nameaccount_type都存在结果行。

select
  s.inst_name,
  sa.account_type,
  count(*) as total
from staffs s
join
(
  select 
    sid, 
    case when count(*) = 1 then 'SINGLE' else 'DOUBLE' end as account_type
  from staffaccounts
  group by sid
  having count(*) <= 2
) sa on sa.sid = s.sid
group by sa.account_type, s.inst_name
order by sa.account_type, s.inst_name;

I got only the way by using subquery but is in the easy way (more easier and readable) to achieve your requirement 只能通过使用subquery但是以一种简单的方式(more easier and readable)可以满足您的要求

SELECT inst_name, account_type, count(total) as total
FROM (
    SELECT
        a.inst_name, 
        CASE 
            WHEN COUNT (b.account_no) = 1 THEN 'Single'
            WHEN COUNT (b.account_no) = 2 THEN 'Double'
        END AS account_type,
        COUNT (a.name) AS total
    FROM staffs a
    INNER JOIN staffaccounts b ON A . SID = b.sid
    GROUP BY a.inst_name, a.sid) t GROUP BY inst_name, account_type

OUTPUT : 输出

inst_name   account_type    total
ABC         Double          2
PQR         Double          1
ABC         Single          1
PQR         Single          1

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM