我在SQL(特别是PostgreSQL)中遇到困难。我正在使用的架构/模型不受我的控制,也不属于我可以更改的东西,因此我试图找出处理已处理过的卡片的最佳方法。
首先,简化了该问题的架构,但实际上是将发票(类型= T)和交易(类型<> T)行组合到同一张表中。每个发票可以有n个交易行,每个客户可以有n个发票。
ID | 类型 | 发票号码 | 客户编号 |
---|---|---|---|
100 | 一世 | 100 | 1个 |
99 | X | 0 | 1个 |
98 | 小号 | 0 | 1个 |
97 | Ť | 0 | 1个 |
96 | 一世 | 99 | 1个 |
95 | X | 0 | 1个 |
94 | 小号 | 0 | 1个 |
我最终希望得到的结果类似于以下内容,其中删除了发票(Type = I)记录,而交易(Type <> T)记录落在每个填充有对应InvoiceId值的发票记录之后。
ID | 类型 | 发票号码 | 客户编号 |
---|---|---|---|
99 | X | 100 | 1个 |
98 | 小号 | 100 | 1个 |
97 | Ť | 100 | 1个 |
95 | X | 99 | 1个 |
94 | 小号 | 99 | 1个 |
到目前为止,我能够获得的最接近的(不是很接近)使用的是以下SQL:
select
t1.Id,
t1.Type,
t2.InvoiceNo,
t1.ClientId
from table AS t1
join (select
Id,
InvoiceNo,
ClientId
from table
where type = 'I') as t2
on t1.ClientId = t2.ClientId
where t1.ClientId = t2.ClientId and t1.Id <= t2.Id and t1.Type <> 'I'
这样的结果如下所示,它对于每个客户的第一个发票都可以正常工作,然后为每个发票创建额外的交易记录
ID | 类型 | 发票号码 | 客户编号 |
---|---|---|---|
99 | X | 100 | 1个 |
98 | 小号 | 100 | 1个 |
97 | Ť | 100 | 1个 |
95 | X | 100 | 1个 |
95 | X | 99 | 1个 |
94 | 小号 | 100 | 1个 |
94 | 小号 | 99 | 1个 |
任何帮助或指导,不胜感激!
**更新了更复杂的示例**
来源:
ID | 类型 | 发票号码 | 客户编号 |
---|---|---|---|
1个 | X | 0 | 1个 |
2 | 一世 | 97 | 1个 |
3 | 小号 | 0 | 2 |
4 | X | 0 | 2 |
5 | 小号 | 0 | 1个 |
6 | 一世 | 98 | 2 |
7 | 小号 | 0 | 1个 |
8 | X | 0 | 1个 |
9 | 一世 | 99 | 1个 |
10 | Ť | 0 | 1个 |
11 | 小号 | 0 | 1个 |
12 | X | 0 | 1个 |
13 | 一世 | 100 | 1个 |
玩下面的答案,我想出了:
select * from (select t.*,
max(InvoiceNo) filter (where type = 'I') over (partition by clientid order by id DESC) as imputed_invoiceno
from t) as x
where Type <> 'I';
这使我接近:
ID | 类型 | 发票号码 | 客户编号 | imputed_invoiceno |
---|---|---|---|---|
12 | X | 0 | 1个 | 100 |
11 | 小号 | 0 | 1个 | 100 |
10 | Ť | 0 | 1个 | 100 |
8 | X | 0 | 1个 | 99 |
7 | 小号 | 0 | 1个 | 99 |
5 | 小号 | 0 | 1个 | 99 |
1个 | X | 0 | 1个 | 99 |
4 | X | 0 | 2 | 98 |
3 | 小号 | 0 | 2 | 98 |
最佳结果:
ID | 类型 | 发票号码 | 客户编号 |
---|---|---|---|
12 | X | 100 | 1个 |
11 | 小号 | 100 | 1个 |
10 | Ť | 100 | 1个 |
8 | X | 99 | 1个 |
7 | 小号 | 99 | 1个 |
5 | 小号 | 99 | 1个 |
1个 | X | 97 | 1个 |
4 | X | 98 | 2 |
3 | 小号 | 98 | 2 |
Based on your sample data, you can use a cumulative window function:
select t.*,
min(invoiceno) filter (where type = 'I') over (order by id desc) as imputed_invoiceno
from t;
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句