简体   繁体   中英

Stored procedure sql server 2008 NOT IN

I have created a query which allows me to view all of the items that have been ordered by customers where the company name = Best Baths using the following code.

Select co.OrderID, cu.FName + '  ' + cu.SName as 'Name', 
cu.Address1 + ', ' + cu.Address2 + ', ' + cu.Address3 as 'Dispatch Address', 
cu.PostCode, 
ma.MaterialName as 'Item',
mi.Price as 'Item Price',
co.DateOrdered as 'Order Date',
pm.DateReceived,

CASE WHEN la.Status = 'Blocked' THEN 'Blocked' ELSE 'Active' END AS Status

from Customers cu
-- inner join the following to find customers orders and cost
inner join CustomerOrder co on co.CustomerID = cu.CustomerID
inner join ItemOrder io on co.ID = io.ItemOrderID
inner join materialItem mi on io.MaterialID = mi.MaterialItemID
inner join Material ma on io.MaterialID = ma.MaterialItemID
left join ItemForInvoice ifi on io.ItemOrderID = ifi.ItemOrderID
left join Invoice iv on ifi.InvoiceItemID = iv.InvoiceItemID
left join PaymentMethod pm on iv.InvoiceID = pm.InvoiceID
left join LockedAccount la on pm.PaymentID = la.PaymentID
inner join Suppliers su on mi.SupplierID = su.SuppliersID
inner join SupplierDetails sd on su.SuppliersID = sd.SuppliersID
Where su.SuppliersName = 'Best Baths'

I now want to create a query thats shows items that have not yet been ordered, can anybody point me in the right direction?

It's not obvious from your query as to what tables what, but the basic query would be something like

SELECT items.id, COUNT(orders.itemid) AS cnt
FROM items
LEFT JOIN orders ON items.id = orders.itemid
GROUP BY items.id
HAVING (cnt = 0)

Annoscia, look this example:

(SELECT coll FROM TableA)
EXCEPT
(SELECT coll FROM TableB)

it's mean:

SELECT DISTINCT coll
  FROM TableA 
 WHERE NOT EXISTS (SELECT * 
                     FROM TableB 
                    WHERE TableA.col1 = TableB.col1)

for your case it will be so:

Select co.OrderID, cu.FName + '  ' + cu.SName as 'Name', 
cu.Address1 + ', ' + cu.Address2 + ', ' + cu.Address3 as 'Dispatch Address', 
cu.PostCode, 
ma.MaterialName as 'Item',
mi.Price as 'Item Price',
co.DateOrdered as 'Order Date',
pm.DateReceived,    
CASE WHEN la.Status = 'Blocked' THEN 'Blocked' ELSE 'Active' END AS Status

from Customers cu
-- inner join the following to find customers orders and cost
inner join CustomerOrder co on co.CustomerID = cu.CustomerID
inner join ItemOrder io on co.ID = io.ItemOrderID
inner join materialItem mi on io.MaterialID = mi.MaterialItemID
inner join Material ma on io.MaterialID = ma.MaterialItemID
left join ItemForInvoice ifi on io.ItemOrderID = ifi.ItemOrderID
left join Invoice iv on ifi.InvoiceItemID = iv.InvoiceItemID
left join PaymentMethod pm on iv.InvoiceID = pm.InvoiceID
left join LockedAccount la on pm.PaymentID = la.PaymentID
inner join Suppliers su on mi.SupplierID = su.SuppliersID
inner join SupplierDetails sd on su.SuppliersID = sd.SuppliersID

EXCEPT

Select co.OrderID, cu.FName + '  ' + cu.SName as 'Name', 
cu.Address1 + ', ' + cu.Address2 + ', ' + cu.Address3 as 'Dispatch Address', 
cu.PostCode, 
ma.MaterialName as 'Item',
mi.Price as 'Item Price',
co.DateOrdered as 'Order Date',
pm.DateReceived,

CASE WHEN la.Status = 'Blocked' THEN 'Blocked' ELSE 'Active' END AS Status

from Customers cu
-- inner join the following to find customers orders and cost
inner join CustomerOrder co on co.CustomerID = cu.CustomerID
inner join ItemOrder io on co.ID = io.ItemOrderID
inner join materialItem mi on io.MaterialID = mi.MaterialItemID
inner join Material ma on io.MaterialID = ma.MaterialItemID
left join ItemForInvoice ifi on io.ItemOrderID = ifi.ItemOrderID
left join Invoice iv on ifi.InvoiceItemID = iv.InvoiceItemID
left join PaymentMethod pm on iv.InvoiceID = pm.InvoiceID
left join LockedAccount la on pm.PaymentID = la.PaymentID
inner join Suppliers su on mi.SupplierID = su.SuppliersID
inner join SupplierDetails sd on su.SuppliersID = sd.SuppliersID
Where su.SuppliersName = 'Best Baths'

If you're after the materials (ie item) that have not yet been ordered, then an NOT EXISTS clause will work well. You only need to check that it has not been involved in an order via ItemOrder table.

Select ma.MaterialName as [Item],
       mi.Price as [Item Price]
  from Material ma
  join materialItem mi on io.MaterialID = mi.MaterialItemID
 where not exists (select *
                     from ItemOrder io
                    where io.MaterialID = ma.MaterialItemID)

PLEASE do not quote column aliases using ( ' ) single quotes in future, use the square brackets.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM