空值联接3个表

时间:2020-06-02 04:16:22

标签: sql sql-server tsql

下面是查询,我已经加入了3个表供应商是主表。实际情况是我希望表应付账款表中的所有数据虽然不是采购订单表中的所有数据,所以我已将FULL Outer与供应商和采购订单一起使用,但供应商详细信息并未与应付账款数据相抵触尽管可以使用供应商密钥。

SELECT ISNULL(dbo.Supplier.supplier_key,dbo.Fact_AccountPayables.supplier_key) AS supplier_key,
                  dbo.Supplier.Supplier,
                  dbo.Supplier.Name,
                  dbo.Supplier.Status, 
                  dbo.Supplier.AddressCode, 
                  dbo.Supplier.Address,
                  dbo.Supplier.HouseNo,
                  dbo.Supplier.Street,
                  dbo.Supplier.City, 
                  dbo.Supplier.Country,
                  dbo.Supplier.ZipCode,
                  dbo.Supplier.StartDate,
                  dbo.Supplier.CreditLimit, 
                  dbo.Supplier.FinancialGroup,
                  dbo.Supplier.LastTransactionDate, 
                  dbo.Fact_PurchaseOrder.Company, 
                  ISNULL(dbo.Fact_PurchaseOrder.[Purchase Order],dbo.Fact_AccountPayables.[PO Number]) AS PurchaseOrder,
                  ISNULL( dbo.Fact_PurchaseOrder.Sequence,dbo.Fact_AccountPayables.Line) AS POSequence, 
                  dbo.Fact_PurchaseOrder.[Order Quantity], 
                  dbo.Fact_PurchaseOrder.[Per Purchase Unit], 
                  dbo.Fact_PurchaseOrder.[Per Quantity Price],
                  dbo.Fact_PurchaseOrder.[Purchase price unit],
                  dbo.Fact_PurchaseOrder.[Total Order Amount],
                  dbo.Fact_PurchaseOrder.Currency, 
                  dbo.Fact_PurchaseOrder.[Rate Date], 
                  dbo.Fact_PurchaseOrder.[Actual Receipt Date],
                  dbo.Fact_PurchaseOrder.[Receipt No],
                  dbo.Fact_PurchaseOrder.[Receipt Sequence], 
                  dbo.Fact_PurchaseOrder.[Received Quantity],
                  dbo.Fact_PurchaseOrder.[Approved Quantity], 
                  dbo.Fact_PurchaseOrder.[Purchase Office], 
                  dbo.Fact_PurchaseOrder.[Invoice Number], 
                  dbo.Fact_PurchaseOrder.[Invoice Date], 
                  dbo.Fact_PurchaseOrder.[Invoice Quantity],
                  dbo.Fact_PurchaseOrder.[Invoice Amount],
                  dbo.Fact_AccountPayables.InvoiceNumber, 
                  dbo.Fact_AccountPayables.Type AS InvoiceType, 
                  dbo.Fact_AccountPayables.[Order Type] AS OrderInvoiceType,
                  dbo.Fact_AccountPayables.AP_Balance_EUR, 
                  dbo.Fact_AccountPayables.[Invoice Amount_EUR],
                  dbo.Fact_AccountPayables.supplier_key AS EXPR2,
                  dbo.Fact_AccountPayables.[IntercompanyTrade Order No] AS EXPR23, 
                  dbo.Fact_AccountPayables.[IntercompanyTrade Line Number] AS EXPR24,
                  dbo.Fact_AccountPayables.[Intercompany Trade Financial Company] AS EXPR25, 
                  dbo.Fact_AccountPayables.[Intercompany Trade Purchase Company] AS EXPR26,
                  dbo.Fact_AccountPayables.InvoiceNumber,
                  dbo.Fact_AccountPayables.DueDate,
                  dbo.Fact_AccountPayables.DocDate, 
                  dbo.Fact_PurchaseOrder.[Order Date],
                  dbo.Fact_AccountPayables.[Invoice Amount_EUR],
                  (CASE WHEN dbo.Fact_PurchaseOrder.[Receipt No] = ' ' THEN dbo.Fact_PurchaseOrder.[Total Order Amount]
                        WHEN  dbo.Fact_PurchaseOrder.[Receipt No] != ' ' and dbo.Fact_AccountPayables.InvoiceNumber IS NULL then dbo.Fact_PurchaseOrder.[Total Order Amount] END) AS ORDERBALANCE,
                  (dbo.Supplier.CreditLimit -(ORDERBALANCE + dbo.Fact_AccountPayables.[Invoice Amount_EUR])) AS Availablecredit
    FROM            dbo.Supplier 
            LEFT OUTER JOIN dbo.Fact_PurchaseOrder ON dbo.Supplier.supplier_key = dbo.Fact_PurchaseOrder.buyfrom_supplier_key
            full OUTER JOIN dbo.Fact_AccountPayables ON dbo.Fact_AccountPayables.supplier_key = dbo.Supplier.supplier_key AND
                                                        dbo.Fact_AccountPayables.[PO Number] = dbo.Fact_PurchaseOrder.[Purchase Order]   AND 
                                                    dbo.Fact_AccountPayables.[PO Line] = dbo.Fact_PurchaseOrder.Sequence

输出如下:

enter image description here

4 个答案:

答案 0 :(得分:0)

您不仅使用了供应商密钥,而且还使用了采购订单编号和采购订单行作为完全外部联接的联接标准。如果在供应商表中没有这些条目的匹配条目(同时所有ALL连接条件的条目匹配),您还将看到您提到的空值。

仅出于测试目的,暂时删除其他加入条件(采购订单号和行),仅保留供应商密钥。检查在这种情况下是否仍然看到空值。

答案 1 :(得分:0)

在该 FROM 条款之后尝试使用您的Payable表,并使用 LEFT JOIN

将其他表连接起来
FROM dbo.Fact_AccountPayables         
LEFT JOIN dbo.Fact_PurchaseOrder ON  dbo.Fact_AccountPayables.[PO Number] =  dbo.Fact_PurchaseOrder.[Purchase Order]   AND 
 dbo.Fact_AccountPayables.[PO Line] =  dbo.Fact_PurchaseOrder.Sequence
LRFT JOIN dbo.Supplier  ON dbo.Supplier.supplier_key = dbo.Fact_PurchaseOrder.buyfrom_supplier_key AND dbo.Fact_AccountPayables.supplier_key = dbo.Supplier.supplier_key 

答案 2 :(得分:0)

您正在对Fact_AccountPayables表使用FULL联接。这样,即使与其他两个表都不匹配,也将包括Fact_AccountPayables中的所有记录。如果您不想这样做,请使用LEFT联接而不是FULL联接。

SELECT
  ISNULL(dbo.Supplier.supplier_key, dbo.Fact_AccountPayables.supplier_key) AS supplier_key,
  dbo.Supplier.Supplier,
  dbo.Supplier.Name,
  dbo.Supplier.Status, 
  dbo.Supplier.AddressCode, 
  dbo.Supplier.Address,
  dbo.Supplier.HouseNo,
  dbo.Supplier.Street,
  dbo.Supplier.City, 
  dbo.Supplier.Country,
  dbo.Supplier.ZipCode,
  dbo.Supplier.StartDate,
  dbo.Supplier.CreditLimit, 
  dbo.Supplier.FinancialGroup,
  dbo.Supplier.LastTransactionDate, 
  dbo.Fact_PurchaseOrder.Company, 
  ISNULL(dbo.Fact_PurchaseOrder.[Purchase Order], dbo.Fact_AccountPayables.[PO Number]) AS PurchaseOrder,
  ISNULL(dbo.Fact_PurchaseOrder.Sequence, dbo.Fact_AccountPayables.Line) AS POSequence,
  dbo.Fact_PurchaseOrder.[Order Quantity], 
  dbo.Fact_PurchaseOrder.[Per Purchase Unit], 
  dbo.Fact_PurchaseOrder.[Per Quantity Price],
  dbo.Fact_PurchaseOrder.[Purchase price unit],
  dbo.Fact_PurchaseOrder.[Total Order Amount],
  dbo.Fact_PurchaseOrder.Currency, 
  dbo.Fact_PurchaseOrder.[Rate Date], 
  dbo.Fact_PurchaseOrder.[Actual Receipt Date],
  dbo.Fact_PurchaseOrder.[Receipt No],
  dbo.Fact_PurchaseOrder.[Receipt Sequence], 
  dbo.Fact_PurchaseOrder.[Received Quantity],
  dbo.Fact_PurchaseOrder.[Approved Quantity], 
  dbo.Fact_PurchaseOrder.[Purchase Office], 
  dbo.Fact_PurchaseOrder.[Invoice Number], 
  dbo.Fact_PurchaseOrder.[Invoice Date], 
  dbo.Fact_PurchaseOrder.[Invoice Quantity],
  dbo.Fact_PurchaseOrder.[Invoice Amount],
  dbo.Fact_AccountPayables.InvoiceNumber, 
  dbo.Fact_AccountPayables.Type AS InvoiceType, 
  dbo.Fact_AccountPayables.[Order Type] AS OrderInvoiceType,
  dbo.Fact_AccountPayables.AP_Balance_EUR, 
  dbo.Fact_AccountPayables.[Invoice Amount_EUR],
  dbo.Fact_AccountPayables.supplier_key AS EXPR2,
  dbo.Fact_AccountPayables.[IntercompanyTrade Order No] AS EXPR23, 
  dbo.Fact_AccountPayables.[IntercompanyTrade Line Number] AS EXPR24,
  dbo.Fact_AccountPayables.[Intercompany Trade Financial Company] AS EXPR25, 
  dbo.Fact_AccountPayables.[Intercompany Trade Purchase Company] AS EXPR26,
  dbo.Fact_AccountPayables.InvoiceNumber,
  dbo.Fact_AccountPayables.DueDate,
  dbo.Fact_AccountPayables.DocDate, 
  dbo.Fact_PurchaseOrder.[Order Date],
  dbo.Fact_AccountPayables.[Invoice Amount_EUR],
  CASE
    WHEN dbo.Fact_PurchaseOrder.[Receipt No] = ' ' THEN dbo.Fact_PurchaseOrder.[Total Order Amount]
    WHEN dbo.Fact_AccountPayables.InvoiceNumber IS NULL THEN dbo.Fact_PurchaseOrder.[Total Order Amount]
  END AS ORDERBALANCE,
  dbo.Supplier.CreditLimit - (ORDERBALANCE + dbo.Fact_AccountPayables.[Invoice Amount_EUR]) AS Availablecredit
FROM
  dbo.Supplier 
  LEFT JOIN dbo.Fact_PurchaseOrder ON dbo.Supplier.supplier_key = dbo.Fact_PurchaseOrder.buyfrom_supplier_key
  LEFT JOIN dbo.Fact_AccountPayables ON
    dbo.Fact_AccountPayables.supplier_key = dbo.Supplier.supplier_key AND
    dbo.Fact_AccountPayables.[PO Number] = dbo.Fact_PurchaseOrder.[Purchase Order]   AND 
    dbo.Fact_AccountPayables.[PO Line] = dbo.Fact_PurchaseOrder.Sequence

答案 3 :(得分:0)

如果某些行没有供应商,则会在Fact_PurchaseOrder中对其进行过滤。您需要为所有表进行FULL OUTER JOIN,以获取AccountPayables所有行的数据,而不管它们是否有供应商。

FROM  dbo.Supplier 
FULL OUTER JOIN dbo.Fact_PurchaseOrder ON dbo.Supplier.supplier_key = dbo.Fact_PurchaseOrder.buyfrom_supplier_key
FULL OUTER JOIN dbo.Fact_AccountPayables ON dbo.Fact_AccountPayables.supplier_key = dbo.Supplier.supplier_key AND
                                                        dbo.Fact_AccountPayables.[PO Number] = dbo.Fact_PurchaseOrder.[Purchase Order]   AND 
                                                    dbo.Fact_AccountPayables.[PO Line] = dbo.Fact_PurchaseOrder.Sequence