SQL两个表,需要根据每个表中的数据来提取

时间:2016-04-18 14:47:45

标签: sql oracle

我正在尝试做一个简单的SQL查询(Oracle),它包含两个表,"修订版"和"预计"。我想总是从"修订版"表,如果存在的话。如果修改后的表格是空白的,那么我需要从" Projected"表。我一直在尝试的不同连接组合不返回我正在寻找的数据。任何帮助表示赞赏!

感谢。

4 个答案:

答案 0 :(得分:0)

你尝试过这样的事吗?

select your columns 
from revised
union all
select your columns 
from projected where not exists (select 1 from revised);

如果修订中没有任何内容,则从修订中选择所有内容,从投影中选择所有内容。

或者,没有exists

select your columns 
from revised
union all
select your columns 
from projected where (select count(*) from revised) = 0;

编辑:在项目级别获取您的需求,只需按项目过滤:

select your columns 
from revised
union all
select your columns 
from projected p where (select count(*) 
                      from revised r
                      where r.Revised_ProjectID = p.Projected_ProjectID) = 0;

答案 1 :(得分:0)

您可以使用大小写和左连接来实现此目的。

 select p.Project_ID,
    case when r.Project_ID is null then p.ProjectedPaymentAmount else r.RevisedPaymentAmount end as PaymentAmount,
    case when r.Project_ID is null then p.ProjectedPaymentDate else r.RevisedPaymentDate end as PaymentDate
from ProjectPayments_Projected p
left join ProjectPayments_Revised r on p.Project_ID = r.Project_ID 

如果项目可以有多个修订版,请使用此项。

;WITH cte AS
(
  SELECT *,
  ROW_NUMBER() OVER (PARTITION BY Project_ID ORDER BY RevisedPaymentDate DESC) AS rn
  FROM ProjectPayments_Revised
)

select p.Project_ID,
    case when r.Project_ID is null then p.ProjectedPaymentAmount else r.RevisedPaymentAmount end as PaymentAmount,
    case when r.Project_ID is null then p.ProjectedPaymentDate else r.RevisedPaymentDate end as PaymentDate
from ProjectPayments_Projected p
left join cte r on r.rn = 1 and r.Project_ID = p.Project_ID

答案 2 :(得分:0)

试试这个。看起来很奇怪。通常有效。

select id, max(amt) amt, max(date) date
from ( select p.id id, p.amt amt, p.date date
         from projected p
       union
       select r.id, r.amt, r.date
         from revised )
group by id;

答案 3 :(得分:0)

因此项目ID总是有Revised条记录,Projected条记录或两者都有。一种方法是外连接表,看看你得到了什么:

select
  case when revised_projectid is not null then revised_projectid else projected_projectid end as project_id,
  case when revised_projectid is not null then revised_amt else projected_amt end as project_amt,
  case when revised_projectid is not null then revised_date else projected_date end as project_date
from revised r
full outer join projected p on p.projected_projectid = r.revised_projectid;

只是为了它的乐趣,这是一个UNION查询得到相同的结果。我们联合了两个表,在途中为它们提供了一个优先级标志。然后我们按照project_id对记录进行排名,给出更好的记录等级1.然后我们关闭其他记录并完成。你看到有很多方法可以解决这个问题: - )

select project_id, project_amt, project_date
from
(
  select 
    project_id, 
    project_amt, 
    project_date, 
    row_number() over (partition by project_id order by priority) as rn
  from
  (
    select 
      1 as priority, 
      revised_projectid as project_id, 
      revised_amt as project_amt, 
      revised_date as project_date
    from revised
    union all
    select 
      2 as priority,
      projected_projectid as project_id, 
      projected_amt as project_amt, 
      projected_date as project_date
    from projected
  )
)
where rn = 1;

我已将第二个查询添加到我的回答中,以便向您显示另一个选项。虽然这次方法可能会更好,但下次遇到类似问题时,另一种方法可能是正确的选择。