我有一个名为employees的表,其中有ID和hire_date列。因此,我需要编写一个查询,输出如下所示: 当hire_date is null为ID=101时,它将给予ID=110的hire_date。反之亦然,当hire_date is null为id=110时,它将给出ID=101的hire date。
SELECT e.*,
CASE
WHEN hire_date IS NULL AND id = 101
THEN COALESCE(
MIN(CASE id WHEN 110 THEN hire_date END) OVER (),
DATE '1900-01-01' -- Default if both NULL
)
WHEN hire_date IS NULL AND id = 110
THEN COALESCE(
MIN(CASE id WHEN 101 THEN hire_date END) OVER (),
DATE '1900-01-01' -- Default if both NULL
)
ELSE hire_date -- value for other rows.
END AS value
FROM employees e;
其中,对于示例数据:
CREATE TABLE employees (id, name, hire_date) AS
SELECT 101, 'Alice', DATE '1970-01-01' FROM DUAL UNION ALL
SELECT 110, 'Beryl', NULL FROM DUAL UNION ALL
SELECT 111, 'Carol', DATE '1980-01-01' FROM DUAL;
SELECT
id,
hire_date,
CASE
WHEN hire_date IS NULL AND id = 101 THEN
( SELECT hire_date FROM employees WHERE id = 110 )
WHEN hire_date IS NULL AND id = 110 THEN
( SELECT hire_date FROM employees WHERE id = 101 )
ELSE
NULL
END AS hire_date2
FROM
employees
-- sample data
WITH
emps AS
(
SELECT 101 "ID", 'John' "NAME", To_Date('01.08.2000', 'dd.mm.yyyy') "HIRE_DATE" FROM DUAL Union All
SELECT 110 "ID", 'Jane' "NAME", Null "HIRE_DATE" FROM DUAL Union All
SELECT 120 "ID", 'Mark' "NAME", To_Date('01.10.2000', 'dd.mm.yyyy') "HIRE_DATE" FROM DUAL
)
-- main SQL
SELECT
ID, NAME, HIRE_DATE,
CASE WHEN ID = 101 THEN Nvl(HIRE_DATE, ( SELECT hire_date FROM emps WHERE id = 110 ) )
WHEN ID = 110 THEN Nvl(HIRE_DATE, ( SELECT hire_date FROM emps WHERE id = 101 ) )
ELSE
HIRE_DATE
END "ALTERNATIVE_HIRE_DATE"
FROM
emps
-- sample data (2)
WITH
emps AS
(
SELECT 101 "ID", 'John' "NAME", Null "HIRE_DATE" FROM DUAL Union All
SELECT 110 "ID", 'Jane' "NAME", Null "HIRE_DATE" FROM DUAL Union All
SELECT 120 "ID", 'Mark' "NAME", To_Date('01.10.2000', 'dd.mm.yyyy') "HIRE_DATE" FROM DUAL
)
-- main SQL
SELECT
ID, NAME, HIRE_DATE,
CASE WHEN ID = 101 THEN Nvl(Nvl(HIRE_DATE, ( SELECT hire_date FROM emps WHERE id = 110 ) ), To_Date('01.01.2000', 'dd.mm.yyyy'))
WHEN ID = 110 THEN Nvl(Nvl(HIRE_DATE, ( SELECT hire_date FROM emps WHERE id = 101 ) ), To_Date('01.01.2000', 'dd.mm.yyyy'))
ELSE
HIRE_DATE
END "ALTERNATIVE_HIRE_DATE"
FROM
emps
3条答案
按热度按时间0kjbasz61#
可以在分析函数中使用条件聚合来避免自联接:
其中,对于示例数据:
输出:
| 识别码|名称|聘用日期|价值|
| - -|- -|- -|- -|
| 一百零一|爱丽斯|1970年01月01日00:00:00| 1970年01月01日00:00:00|
| 第一百一十章|绿柱石| * 空值 *| 1970年01月01日00:00:00|
| 一一一|卡罗尔|1980年01月01日00:00:00| 1980年01月01日00:00:00|
fiddle
wvyml7n52#
你是说像这样?
nlejzf6q3#
这样试试看...
结果:
| 识别码|名称|聘用日期|替代聘用日期|
| - -|- -|- -|- -|
| 一百零一|若翰|2000年8月1日|2000年8月1日|
| 第一百一十章|简||2000年8月1日|
| 一百二十个|标记|2000年10月1日|2000年10月1日|
如果两个hiredate(id 101和110)中都有空值的可能性,那么可以使用嵌套的Nvl()函数来实现。
结果:
| 识别码|名称|聘用日期|替代聘用日期|
| - -|- -|- -|- -|
| 一百零一|若翰||2000年1月1日|
| 第一百一十章|简||2000年1月1日|
| 一百二十个|标记|2000年10月1日|2000年10月1日|