使用ORACLE SQL。
我有一个表格“Employees
”,其中一个属性为“hire_date
”。我的任务(书籍练习)是写一个SELECT
,它将告诉我在1995年,1996年,1997年和1998年雇用了多少员工。
类似的东西:
TOTAL 1995 1996 1997 1998
-----------------------------------------
20 4 5 29 2
单独计算每年的员工数量很容易,例如:
SELECT
COUNT(*),
FROM
employees e
WHERE
e.hire_date like '%95'
但是当我必须以所需格式“聚合”数据时,我遇到了困难。 有什么建议吗?
答案 0 :(得分:5)
我假设您的hire_date是varchar2,因为您在示例中执行了“like”子句。
每年一行的简单表会吗?
如果是这样,请在Oracle中尝试:
select case grouping(hire_date)
when 0 then hire_date
else 'TOTAL'
end hire_date,
count(hire_date) as count_hire_date
from employees
group by rollup(hire_date);
这应该是这样的:
hire_date count_hire_date
1995 10
1996 20
1997 30
TOTAL 60
如果您确实需要将结果转换为您在问题中显示的内容,那么如果您知道运行查询之前的不同年份,则可以执行以下操作。例如,如果你知道你的表中只有1995,1996和1997,那么你可以用这个来转动结果:
SELECT
MAX(CASE WHEN hire_date = 'TOTAL' THEN ilv.count_hire_date END) total,
MAX(CASE WHEN hire_date = '1995' THEN ilv.count_hire_date END) count_1995,
MAX(CASE WHEN hire_date = '1996' THEN ilv.count_hire_date END) count_1996,
MAX(CASE WHEN hire_date = '1997' THEN ilv.count_hire_date END) count_1997
from (
select case grouping(hire_date)
when 0 then hire_date
else 'TOTAL'
end hire_date,
count(hire_date) as count_hire_date
from employees
group by rollup(hire_date)
) ilv;
这有一个明显的缺点,你需要在每个可能的年份的主select语句中添加一个新子句。
答案 1 :(得分:4)
语法不直观。这利用了cut'n'paste编码:
SQL> select
2 sum(case when to_char(hiredate, 'YYYY') = '1980' then 1 else 0 end) as "1980"
3 , sum(case when to_char(hiredate, 'YYYY') = '1981' then 1 else 0 end) as "1981"
4 , sum(case when to_char(hiredate, 'YYYY') = '1982' then 1 else 0 end) as "1982"
5 , sum(case when to_char(hiredate, 'YYYY') = '1983' then 1 else 0 end) as "1983"
6 , sum(case when to_char(hiredate, 'YYYY') = '1987' then 1 else 0 end) as "1987"
7 , count(*) as total
8 from emp
9 /
1980 1981 1982 1983 1987 TOTAL
---------- ---------- ---------- ---------- ---------- ----------
1 10 1 0 2 20
Elapsed: 00:00:00.00
SQL>
答案 2 :(得分:1)
以下是我将如何在MS SQL中执行此操作 - 它在Oracle中类似,但我不想尝试为您提供Oracle代码,因为我通常不会编写它。这只是为了给你一个基本的骨架。
Select
Year(e.hire_date),
Count(1)
From
employees e
Group By
Year(e.hire_date)
答案 3 :(得分:1)
以下是我在MySQL中的做法,不知道这是否也适用于Oracle:
SELECT
YEAR(hire_date), COUNT(*)
FROM
employees
GROUP BY
YEAR(hire_date)
答案 4 :(得分:1)
SELECT NVL(hire_date,'Total'), count(hire_date)
FROM Employees GROUP BY rollup(hire_date);
如果您需要PIVOT数据,请参阅A_M的答案。如果您有多年没有数据,但仍希望年份显示零计数,您可以执行以下操作:
SELECT NVL(a.Year,b.Year), NVL2(a.Year,a.Count,0) FROM
(
SELECT NVL(hire_date,'Total') Year, count(hire_date) Count
FROM Employees GROUP BY rollup(hire_date)
) a
FULL JOIN
(
SELECT to_char(2000 + rownum,'FM0000') Year FROM dual CONNECT BY rownum<=9
) b ON a.Year = b.Year;
这是一些测试数据。
create table Employees (hire_date Varchar2(4));
insert into Employees values ('2005');
insert into Employees values ('2004');
insert into Employees values ('2006');
insert into Employees values ('2009');
insert into Employees values ('2009');
insert into Employees values ('2005');
insert into Employees values ('2004');
insert into Employees values ('2006');
insert into Employees values ('2006');
insert into Employees values ('2006');
答案 5 :(得分:0)
我意识到这是6年前的事了,但我还发现了另一种使用Oracle中的DECODE功能的独特方式。
select
count(decode(to_char(hire_date, 'yyyy') , '2005', hire_date, null)) hired_in_2005,
count(decode(to_char(hire_date, 'yyyy') , '2006', hire_date, null)) hired_in_2006,
count(decode(to_char(hire_date, 'yyyy') , '2007', hire_date, null)) hired_in_2007,
count(*) total_emp
from employees
where to_char(hire_date,'yyyy') IN ('2005','2006','2007')