2017-01-26 41 views
2

我遇到了一些麻烦,在不同的表比较的相关数据,我会很感激得到下面的话题有些帮助。不幸的是,我不确定DBS是什么(尽管没有什么优势),但是在IBM硬件上运行它。因此,为了简化数据集:SQL选择性分组

发票

Doci   Sumi 
1005   10 
1006   15 
1007   7 
1008   20 

付款

Docp  Sump 
1006   -15 
1005   -4 
1005   -6 
1007   -7 

的目的是比较两个表,并查看是否有匹配 - 本质上,如果发票金额已覆盖付款与否。对我来说,第一件新事情是比较另一个图表中负数值的数字数据,但是让它与-1乘数一起工作。

剩下的问题,我不能真正拿出一个解决方案基本上使查询了解记录/发票号1005是覆盖,只有两个交易。基本上,结果应该只是发票编号1008,因为它在支付表中没有匹配。

我确实最终审查了SQL集合函数,即SUM,但是实际上并没有弄清楚如何利用它,因为我不想总结整个Sump列中的值,但只有那些具有相同记录的值在Docp专栏中。

到目前为止,我已经是这样的:

SELECT * from INVOICES 
inner join PAYMENTS on INVOICES.Doci = PAYMENTS.Docp 
where Sumi <> (Sump*-1) 

所以,这个查询的工作来,我不会得到记录,例如在结果1006和1007的范围内,但我得到1005,为看似值10相比4,而不是4 + 6

提前任何反馈

非常感谢!

+1

再来想想,我真的不太清楚您想要的结果 –

回答

2

您可以找到每个DOCP的总池,然后用基于文档的发票表连接,并总结

select i.* from invoices i 
inner join (
    select 
     docp, 
     sum(sump) sump 
    from payments 
    group by docp 
) p on i.doci = p.docp 
and i.sumi + p.sump <> 0 
0

试试这个,它会给你只奥斯坦丁量。

declare @inv table (Doci int, Sumi decimal) 
insert @inv values (1005, 10), (1006, 15), (1007, 7), (1008, 20) 

declare @pmt table (Docp int, Sump decimal) 
insert @pmt values (1005, -4), (1006, -15), (1007, -7), (1005, -6) 

;with payments(doc, amt) 
as (
    select Docp, sum(Sump) 
    from @pmt 
    group by Docp 
) 
select Doci, Sumi + isnull(amt,0) as Remaining 
from @inv 
left outer join payments p on p.doc = Doci 
where (Sumi + isnull(amt,0)) <> 0 

结果:

Doci  Remaining 
----------- ---------- 
1008  20 
0

我分两步做的? - 不得不它们组合在一起,以确定是否有多次支付,以及是否平衡的发票或不:

SELECT doci, sumi, docp, sum(sump) as Sump INTO #Step1 
from #INVOICES 
inner join PAYMENTS on INVOICES.Doci = PAYMENTS.Docp 
GROUP BY 
doci, sumi, docp 

GO 

SELECT * from INVOICES 
inner join #PAYMENTS on #INVOICES.Doci = #PAYMENTS.Docp 
where Sumi <> (Sump*-1) AND doci NOT IN (select doci from #step1 WHERE sumi+Sump = 0) 

的结果是一个空的数据集,因为它只会返回值,其中支付不足以覆盖发票(!或太多)

所有在你的榜样的ID必须匹配(即支付==发票)

0

您需要分解问题成为步骤:

首先总和付款它是ID,Docp。让我们调用这个查询的结果PAYMENT_SUM。我们可以调用这个查询的结果PAYMENT_SUM。

然后将其与发票进行比较。

select 
    I.Doci, 
    I.sumi + P.payment_sum as diff 
from INVOICES I 
left join PAYMENT_SUM P 
on I.Doci = P.Docp 
; 

这会给你一个结果为:

Doci diff 
1005 0 
1006 0 
1007 0 
1008 null 

现在看看这个结果,你可以多一个子句添加到查询来选择你想要的东西。 如果要选择具有不匹配的所有付款方的发票,然后条款将

where P.Docp is null 

或者,如果你也想拥有它有一个匹配的付款的发票,但量不能完全覆盖,则:

where (P.Docp is null) or ((I.sumi + P.payment_sum) <> 0) 

现在,所有的步骤组合:

select 
     I.Doci, 
     I.sumi + P.payment_sum as diff 
    from INVOICES as I 
    left join (
     select 
      Docp, 
      SUM(Sump) as payment_sum 
     from PAYMENTS 
     group by Docp 
    ) as P 
    on I.Doci = P.Docp 

    where (P.Docp is null) or (I.sumi + P.payment_sum) <> 0 
    ;