【问题标题】:How to substract between two tables如何在两个表之间进行减法
【发布时间】:2017-06-20 17:54:51
【问题描述】:

我将用另一列的对应值减去一列中具有相同 ID 的值的总和(这些具有相同的数据)。如果AMT列中的值只做一次就只做差值。

所以我想要 AMT(表 A)和 AMT(表 B)之间的区别,它们具有相同的 ID、CRD、STN 和不同的 TYPE。

表 A:

AMT     ID      CRD     STN     TYPE
------- ------- ------- ------- ----
22000   7123344 556677  442233  0200
22000   7123344 556677  442233  0200
22000   7123344 556677  442233  0200
11500   7132323 992211  556611  0200
10000   7132323 992211  556611  0200
35200   7199933 223344  989898  0200

表 B:

AMT     ID      CRD     STN     TYPE
------- ------- ------- ------- ----
67000   7123344 556677  442233  0220
20000   7132323 992211  556611  0220
35300   7199933 223344  989898  0220

我想要得到的结果:

DIFF
----
1000
-1500
100

【问题讨论】:

  • 这将是一个非常基本的查询,通过连接和分组来完成此操作。你写过很多 SQL 吗?
  • 你应该真正展示你尝试过的东西以及为什么它不起作用。为什么第三个差异是 100 - 应该是哪个 ID?您是否需要对仅在(任一)表中的数据有所不同?以及差异的绝对值(在您的示例中,前两个之一为正,另一个为负)?
  • 我更正了。问候,
  • @AlexPoole 你能给我一个建议吗,因为我已经用正确的结果编辑了表格。我尝试了这个查询,但得到的结果是:-22000;-22000;-22000;-11500;-10000;-35200。所以正确的应该是: DIFF ---- 1000 -1500 100 所有记录都是我没有任何值“0”或空值的值。
  • @AlexPoole 我已经编辑过了,对不起!请问你有什么建议吗?亲切的问候,

标签: sql oracle


【解决方案1】:

您的示例输出与表格数据不匹配;如果我们可以忽略 100 值,那么您可能想要这样的东西(在 CTE 中提供表数据):

with table_a (AMT, ID, CRD, STN, TYPE) as (
            select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 11500, 7132323, 992211, 556611, 0200 from dual
  union all select 10000, 7132323, 992211, 556611, 0200 from dual
  union all select 35200, 7178866, 223344, 989898, 0200 from dual
),
table_b (AMT, ID, CRD, STN, TYPE) as (
            select 67000, 7123344, 556677, 442233, 0220 from dual
  union all select 20000, 7132323, 992211, 556611, 0220 from dual
  union all select 67100, 7199933, 667733, 343433, 0220 from dual
)
select a.id, a.crd, a.stn, a.sum_amt, b.sum_amt, a.sum_amt - b.sum_amt as diff
from (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_a
  group by id, crd, stn, type
) a
inner join (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_b
  group by id, crd, stn, type
) b
on b.id = a.id and b.crd = a.crd and b.stn = a.stn and b.type != a.type
order by a.id, a.crd, a.stn;

        ID        CRD        STN    SUM_AMT    SUM_AMT       DIFF
---------- ---------- ---------- ---------- ---------- ----------
   7123344     556677     442233      66000      67000      -1000
   7132323     992211     556611      21500      20000       1500

子查询(内联视图)为每个 ID/CRD/STN/TYPE 生成总和,然后将它们连接在一起,这样就可以减去等价的总和。即便如此,您的结果仍然是正数;如果这是你想要的,那么你可以修改它来做

abs(a.sum_amt - b.sum_amt) as diff

或者您可能希望减法采用相反的方式,因此您得到 +1000 和 -1500。

您可能还想要只存在于表 A 中的组合的差异:

select a.id, a.crd, a.stn, a.sum_amt, b.sum_amt,
  coalesce(a.sum_amt, 0) - coalesce(b.sum_amt, 0) as diff
from (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_a
  group by id, crd, stn, type
) a
left outer join (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_b
  group by id, crd, stn, type
) b
on b.id = a.id and b.crd = a.crd and b.stn = a.stn and b.type != a.type
order by a.id, a.crd, a.stn;

        ID        CRD        STN    SUM_AMT    SUM_AMT       DIFF
---------- ---------- ---------- ---------- ---------- ----------
   7123344     556677     442233      66000      67000      -1000
   7132323     992211     556611      21500      20000       1500
   7178866     223344     989898      35200                 35200

或出现在表 A 或表 B 或两者中的组合:

select coalesce(a.id, b.id) as id, coalesce(a.crd, b.crd) as crd,
  coalesce(a.stn, b.stn) as stn, a.sum_amt, b.sum_amt,
  coalesce(a.sum_amt, 0) - coalesce(b.sum_amt, 0) as diff
from (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_a
  group by id, crd, stn, type
) a
full outer join (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_b
  group by id, crd, stn, type
) b
on b.id = a.id and b.crd = a.crd and b.stn = a.stn and b.type != a.type
order by coalesce(a.id, b.id), coalesce(a.crd, b.crd), coalesce(a.stn, b.stn);

        ID        CRD        STN    SUM_AMT    SUM_AMT       DIFF
---------- ---------- ---------- ---------- ---------- ----------
   7123344     556677     442233      66000      67000      -1000
   7132323     992211     556611      21500      20000       1500
   7178866     223344     989898      35200                 35200
   7199933     667733     343433                 67100     -67100

这些使用左外连接或全外连接,并添加coalesce() 调用来处理一个内联视图或另一个内不存在的数据。


使用您修改后的数据,并反转计算以获得您想要的符号,这将得到您预期的结果:

with table_a (AMT, ID, CRD, STN, TYPE) as (
            select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 22000, 7123344, 556677, 442233, 0200 from dual
  union all select 11500, 7132323, 992211, 556611, 0200 from dual
  union all select 10000, 7132323, 992211, 556611, 0200 from dual
  union all select 35200, 7199933, 223344, 989898, 0200 from dual
),
table_b (AMT, ID, CRD, STN, TYPE) as (
            select 67000, 7123344, 556677, 442233, 0220 from dual
  union all select 20000, 7132323, 992211, 556611, 0220 from dual
  union all select 35300, 7199933, 223344, 989898, 0220 from dual
)
select a.id, a.crd, a.stn, a.sum_amt, b.sum_amt, b.sum_amt - a.sum_amt as diff
from (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_a
  group by id, crd, stn, type
) a
inner join (
  select id, crd, stn, type, sum(amt) as sum_amt
  from table_b
  group by id, crd, stn, type
) b
on b.id = a.id and b.crd = a.crd and b.stn = a.stn and b.type != a.type
order by a.id, a.crd, a.stn;

        ID        CRD        STN    SUM_AMT    SUM_AMT       DIFF
---------- ---------- ---------- ---------- ---------- ----------
   7123344     556677     442233      66000      67000       1000
   7132323     992211     556611      21500      20000      -1500
   7199933     223344     989898      35200      35300        100

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-03-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-03-07
    • 2018-03-19
    • 2019-05-31
    相关资源
    最近更新 更多