3

快乐星期五乡亲,加入一个表,两个一一对多的关系表中的SQL Server

我试图写一个SSRS报告从三个显示数据(实际上约12个,但只有三个相关)表它们之间存在不协调的关系,数据背后的SQL查询很困难。

涉及三个实体 - 采购订单,销售订单和交货。问题是一个采购订单可能有许多销售订单,还有很多没有与销售订单相关的交货......这太容易了。

销售订单和交货表均可通过外键和中间表链接到采购订单表。

我需要基本上列出采购订单,销售订单列表和他们旁边的交货清单,对于任何无效的字段都使用NULL,以便在SSRS中提供所需的输出/一个人,即对于具有2个销售订单和4个交货日期的采购订单;

PO SO  Delivery 
1234 ABC  05/10 
1234 DEF  09/10 
1234 NULL 10/12 
1234 NULL 14/12 

以上(按PO分组时)会告诉用户有两个销售订单和四个(未链接)交货日期。

同样,如果有比交付更多的SO,我们需要在交货栏中为空;

PO SO  Delivery 
1234 ABC  03/08 
1234 DEF  NULL 
1234 GHI  NULL 
1234 JKL  NULL 

以上是4个SO和一个交货日期的情况。

单独使用左外连接会产生太多重复 - 在本例中为8行,因为它为销售订单上的每个匹配提供了4个交付日期;

PO SO  Delivery 
1234 ABC  05/10 
1234 ABC  09/10 
1234 ABC  10/12 
1234 ABC  14/12  
1234 DEF  05/10 
1234 DEF  09/10 
1234 DEF  10/12 
1234 DEF  14/12 

它的罚款,该PO列被复制为SSRS可以直观该组 - 但SO /交货字段不能被允许复制,因为这无法摆脱的报告 - 如果我将SSRS中的列分组为SO,那么它仍然会为每个分发4个交付日期。

我们的查询很好的唯一情况是当每个PO只有一个SO时。在这种情况下,单个PO和SO号码被复制在一起用于x次交付,并且可以整齐分组到SSRS中。不幸的是,这是一个罕见的数据发生。

我想过尝试使用某种窗口功能或CROSS APPLY,但都因为它们会重复列出的每个采购订单号并最终吐出太多数据而失败。

在想这点恰恰是基于集合的不够是可行的SQL,我知道数据是可怕..

任何帮助非常赞赏。

编辑 - 基本sqlfiddle链接到表模式。省略许多不相关的列。 http://sqlfiddle.com/#!2/5ba16

示例数据...

Purchase Order 
PO_Number Style 
1001  Black work boots 
1002  Green hat 
1006  Red Scarf 

Sales Order 
Sales_order_number PO_number Qty Retailer 
A100-21    1001   15 Walmart 
A100-22    1001   29 Walmart 
A200-31    1006   1000 Asda 

Delivery 
Delivery_ID  Delivery_Date PO_number 
1543285   10/05/2014  1001 
1543286   12/05/2014  1001 
1543287   17/05/2014  1001 
1543288   21/05/2014  1002 
+0

你可以你的实体模型表格作为sqlfidle? (注意DDL是v.limited 8000个最大值)else:提供每个表格数据的简单样本(不是结合的结果) –

+0

这个有用吗? - http://sqlfiddle.com/#!2/5ba16 - 每张表格中都有更多的数据,但所有数据都是针对单个表格(即各种与交付相关的日期,有关所购产品的各种信息)与加入有关。 – lexfury

+0

这是一些真正需要的数据样本 –

回答

1

如果您分配行号在SalesOrders表和交付的元素,你可以链接。

像这样的事情

declare @salesorders table (po int, so varchar(10)) 
declare @deliveries table (po int, delivery date) 
declare @purchaseorders table (po int) 
insert @purchaseorders values (123),(456) 

insert @salesorders values (123,'a'),(123,'b'),(456,'c') 
insert @deliveries values (123,'2014-1-1'),(456,'2014-2-1'),(456,'2014-2-1') 


select * 
from 
( 
    select numbers.number, p.po, so.so, d.delivery from @purchaseorders p 
    cross join (Select number from master..spt_values where type='p') numbers   
    left join (select *,ROW_NUMBER() over (partition by po order by so) sor from @salesorders) so 
     on p.po = so.po and numbers.number = so.sor 
    left join (select * , ROW_NUMBER() over (partition by po order by delivery) dor from @deliveries) d 
     on p.po = d.po and numbers.number = d.dor 
) v 
where so is not null or delivery is not null 
order by po,number   
+0

谢谢podiluska - 辉煌。把你的主题和应用到我的表(他们都有更多的非关键行需要包括),并最终得到它的工作。会投票,但需要15名代表,只是签署了stackexchange(从来没有问过!) – lexfury

相关问题