Sadly, another variation on the popular "Greatest-N-Per-Group" query, but it's been kicking my butt and I could really use some clarity (problem simplified as much as possible):
I've got two tables:
Items
-----
ItemID
ProductName
Inventory
---------
InventoryID
ItemID
Condition
Price
And I'm trying to formulate a query which shows the InventoryID, ItemID, ItemName, Condition, and Max prices for each item In a Given Condition
ie given
Inventory
---------
InventoryID ItemID Condition Price
INV123 ITEM001 NEW $3.99
INV001 ITEM001 NEW $3.79
INV031 ITEM001 USED $1.23
INV234 ITEM001 USED $1.99
And Items:
ItemID ItemName
ITEM001 Lg Widget
ITEM002 Sm Widget
I'd Expect:
ItemID ItemName Condition MaxPrice MaxPriceInventoryID
ITEM001 Lg Widget NEW $3.99 INV123
ITEM001 Lg Widget USED $1.99 INV234
I'm trying this:
SELECT
ItemID, ItemName, b.condition, b.maxprice,
InventoryID as MaxPriceInventoryID
FROM
Items I join inventory v On i.ItemID= v.ItemID
join (
select inventory.ItemID, max(Price) as MaxPrice, condition
from inventory join Items on inventory.ItemID = Items.ItemID
group by inventory.ItemID, condition) as b
on b.ItemID = v.ItemID and b.MaxPrice = v.Price
ORDER BY
ItemName, Condition
Unfortunately, this doesn't give the desired result: it seems to sporadically return max price for the item across all conditions, not max price for the item in a given condition
Ideas?
It's not entirely clear to me precisely how your data are related or how you need to filter.
I'd either do it this way:
SELECT ii.ItemID
,ii.ItemName
,ii.Condition
,ii.Price AS MaxPrice
,ii.MaxPriceInventoryID
FROM (
SELECT i.ItemID
,i.ItemName
,i.ProductName
,v.InventoryID
,v.Condition
,v.Price
,DENSE_RANK() OVER (PARTITION BY v.ItemID, v.Condition ORDER BY v.Price DESC) AS R
FROM Items i
INNER JOIN Inventory v
ON i.ItemID = v.ItemID
WHERE 1 = 1 /* Place your filtering conditionals here */
) AS ii
WHERE ii.R = 1
ORDER BY ii.ItemName
,ii.Condition
Or this way:
SELECT i.ItemID
,i.ItemName
,vv.Condition
,vv.Price AS MaxPrice
,vv.MaxPriceInventoryID
FROM Items i
INNER JOIN (
SELECT v.ItemID
,v.InventoryID
,v.Condition
,v.Price
,DENSE_RANK() OVER (PARTITION BY v.ItemID, v.Condition ORDER BY v.Price DESC) AS R
FROM Inventory v
WHERE 1 = 1 /* Place your filtering conditionals here */
) AS vv
ON i.ItemID = vv.ItemID
WHERE vv.R = 1
ORDER BY i.ItemName
,vv.Condition
If you only want one ItemID even when you have ties on price, then you can replace DENSE_RANK()
with ROW_NUMBER()
. However, unless you add a key field to your ORDER BY
in the OVER()
clause, the result will not be deterministic.
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.