[英]How to find a specific date using Oracle SQL for employee in most current department?
我试图确定在其最近部门的记录(见下面的数据)雇员的最小有效日期。 我期待有2014年8月25日的结果,而是想从你一些专家协助那里就如何把它关闭。 在相同的数据,该员工在部门70260一会儿,然后转移时间以70210短的一段时间,然后回来70260.的2014年8月25日生效日期为当日的员工回来和我倒要看看是否有编程SQL显示某人的最小日期在其最近部门的任何创造性的方式。 提前致谢!!!
╔═══════════╦════════════╦════════╗
║ EMPLID ║ EFFDT ║ DEPTID ║
╠═══════════╬════════════╬════════╣
║ 000123338 ║ 10/25/2015 ║ 70260 ║
║ 000123338 ║ 4/2/2015 ║ 70260 ║
║ 000123338 ║ 2/24/2015 ║ 70260 ║
║ 000123338 ║ 11/1/2014 ║ 70260 ║
║ 000123338 ║ 8/25/2014 ║ 70260 ║ <--- I need the SQL to show 8/25/2014
║ 000123338 ║ 4/27/2014 ║ 70210 ║
║ 000123338 ║ 3/16/2014 ║ 70210 ║
║ 000123338 ║ 3/6/2014 ║ 70260 ║
║ 000123338 ║ 11/1/2013 ║ 70260 ║
║ 000123338 ║ 1/24/2013 ║ 70260 ║
║ 000123338 ║ 1/1/2013 ║ 70260 ║
║ 000123338 ║ 11/1/2012 ║ 70260 ║
║ 000123338 ║ 11/1/2011 ║ 70260 ║
║ 000123338 ║ 8/1/2010 ║ 70260 ║
║ 000123338 ║ 8/5/2009 ║ 70260 ║
║ 000123338 ║ 7/1/2009 ║ 70260 ║
║ 000123338 ║ 7/7/2008 ║ 70260 ║
║ 000123338 ║ 5/5/2008 ║ 70260 ║
║ 000123338 ║ 1/1/2008 ║ 70260 ║
║ 000123338 ║ 10/29/2007 ║ 70260 ║
╚═══════════╩════════════╩════════╝
你可以做这样的事情
select * from
(select empid,effdt,deptid,
row_number() over ( partition by deptid order by effdt desc) as mostRecent
from yourtable) a
where a.mostRecent=1
您可以结合使用窗口聚合功能和最终的全局聚合:
select empid,
deptid,
min(effdt) min_effdt
from (select empid,
deptid,
row_number() over
(partition by empid order by effdt desc) as rn1,
row_number() over
(partition by empid, deptid order by effdt desc) as rn2
from tbl) t
where rn1 = rn2
group by empid,
deptid
内部查询返回这些行号,而外部查询从其余记录(具有RN1 = RN2)中获取最小日期。
╔═══════════╦════════════╦════════╦═════╦═════╦═══════════╗
║ EMPLID ║ EFFDT ║ DEPTID ║ RN1 ║ RN2 ║ MIN_EFFDT ║
╠═══════════╬════════════╬════════╬═════╬═════╬═══════════╣
║ 000123338 ║ 10/25/2015 ║ 70260 ║ 1 ║ 1 ║ ║
║ 000123338 ║ 4/02/2015 ║ 70260 ║ 2 ║ 2 ║ ║
║ 000123338 ║ 2/24/2015 ║ 70260 ║ 3 ║ 3 ║ ║
║ 000123338 ║ 11/01/2014 ║ 70260 ║ 4 ║ 4 ║ ║
║ 000123338 ║ 8/25/2014 ║ 70260 ║ 5 ║ 5 ║ 8/25/2014 ║
║ 000123338 ║ 4/27/2014 ║ 70210 ║ 6 ║ 1 ╠═══════════╝
║ 000123338 ║ 3/16/2014 ║ 70210 ║ 7 ║ 2 ║
║ 000123338 ║ 3/06/2014 ║ 70260 ║ 8 ║ 6 ║
║ 000123338 ║ 11/01/2013 ║ 70260 ║ 9 ║ 7 ║
║ 000123338 ║ 1/24/2013 ║ 70260 ║ 10 ║ 8 ║
║ 000123338 ║ 1/01/2013 ║ 70260 ║ 11 ║ 9 ║
║ 000123338 ║ 11/01/2012 ║ 70260 ║ 12 ║ 10 ║
║ 000123338 ║ 11/01/2011 ║ 70260 ║ 13 ║ 11 ║
║ 000123338 ║ 8/01/2010 ║ 70260 ║ 14 ║ 12 ║
║ 000123338 ║ 8/05/2009 ║ 70260 ║ 15 ║ 13 ║
║ 000123338 ║ 7/01/2009 ║ 70260 ║ 16 ║ 14 ║
║ 000123338 ║ 7/07/2008 ║ 70260 ║ 17 ║ 15 ║
║ 000123338 ║ 5/05/2008 ║ 70260 ║ 18 ║ 16 ║
║ 000123338 ║ 1/01/2008 ║ 70260 ║ 19 ║ 17 ║
║ 000123338 ║ 10/29/2007 ║ 70260 ║ 20 ║ 18 ║
╚═══════════╩════════════╩════════╩═════╩═════╝
您需要找到第一组行:
SELECT EMPLID, MIN(first_dates)
FROM
(
SELECT EMPLID, EFFDT, DEPTID,
CASE -- check if all previous rows return the same value
WHEN MIN(DEPTID) OVER (PARTITION BY EMPLID ORDER BY EFFDT DESC ROWS UNBOUNDED PRECEDING)
= MAX(DEPTID) OVER (PARTITION BY EMPLID ORDER BY EFFDT DESC ROWS UNBOUNDED PRECEDING)
THEN EFFDT
END AS first_dates -- all other rows return NULL
FROM tab
) dt
GROUP BY 1;
如果要整行,则需要添加另一个ROW_NUMBER:
SELECT ...
FROM
(
SELECT ...,
ROW_NUMBER() OVER (PARTITION BY EMPLID ORDER BY first_dates) AS rn
FROM
(
SELECT EMPLID, EFFDT, DEPTID,
CASE
WHEN MIN(DEPTID) OVER (PARTITION BY EMPLID ORDER BY EFFDT DESC ROWS UNBOUNDED PRECEDING)
= MAX(DEPTID) OVER (PARTITION BY EMPLID ORDER BY EFFDT DESC ROWS UNBOUNDED PRECEDING)
THEN EFFDT
END AS first_dates
FROM tab
) dt
) dt
WHERE rn = 1
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.