Please start any new threads on our new site at https://forums.sqlteam.com. We've got lots of great SQL Server experts to answer whatever question you can come up with.

 All Forums
 SQL Server 2005 Forums
 Transact-SQL (2005)
 Dizzy, complex subquery

Author  Topic 

speno
Starting Member

18 Posts

Posted - 2008-03-11 : 18:03:43
I have a piececount table for products with 9 unique fields, or attributes, and 1 field with piececount. I am trying to join it to a product table which also has the 9 unique attributes. Many of the products share the same piece count and there are over 800 products. So rather than maintaining a piece count for each individual product, I'm trying to do this using subqueries.

Hopefully I can explain further. The zero values represent an 'All' value so that each product where explicit values of 1 or greater are linked to a product will use the same piececount except when an explicit value is used.

Piececount table:
specie thick grade length width moisture surface pack ply piececount
1 1 0 1 1 1 0 0 0 10
1 1 1 1 1 1 7 0 0 20

Product Table:
specie thick grade length width moisture surface pack ply description
1 1 1 1 1 1 1 1 1 xxxxx
1 1 1 1 1 1 7 1 1 sssss
1 1 1 1 1 1 2 1 1 ttttt

the 1st and 3rd product should return 10 for piececount. the 2nd product should return 20.

I've spent over a week trying to resolve this. Any help is appreciated.

Lamprey
Master Smack Fu Yak Hacker

4614 Posts

Posted - 2008-03-11 : 19:27:46
For the 2nd product... It matches both rows in the PieceCount table. What are the rules to resolve this? My assumption is that the matching is based on a "more accurate" match. In this case the 2nd product has a 7 and although that matches to a 0 an actual match to a 7 is weighted higher..? If that is the case, here is a possible solution:
DECLARE @PieceCount TABLE 
(
specie INT,
thick INT,
grade INT,
length INT,
width INT,
moisture INT,
surface INT,
pack INT,
ply INT,
piececount INT
)

INSERT @Piececount
SELECT 1, 1, 0, 1, 1, 1, 0, 0, 0, 10
UNION ALL SELECT 1, 1, 1, 1, 1, 1, 7, 0, 0, 20

DECLARE @Product TABLE
(
specie INT,
thick INT,
grade INT,
length INT,
width INT,
moisture INT,
surface INT,
pack INT,
ply INT,
description VARCHAR(50)
)

INSERT @Product
SELECT 1, 1, 1, 1, 1, 1, 1, 1, 1, 'xxxxx'
UNION ALL SELECT 1, 1, 1, 1, 1, 1, 7, 1, 1, 'sssss'
UNION ALL SELECT 1, 1, 1, 1, 1, 1, 2, 1, 1, 'ttttt'

SELECT
Description,
PieceCount
FROM
(
SELECT
P.Description,
C.PieceCount,
--) AS Confidence,
ROW_NUMBER() OVER
(
PARTITION BY
P.Description
ORDER BY
-- Used to weight the match
MAX(CASE WHEN P.specie = C.specie THEN 1 ELSE 0 END
+ CASE WHEN P.thick = C.thick THEN 1 ELSE 0 END
+ CASE WHEN P.grade = C.grade THEN 1 ELSE 0 END
+ CASE WHEN P.length = C.length THEN 1 ELSE 0 END
+ CASE WHEN P.width = C.width THEN 1 ELSE 0 END
+ CASE WHEN P.moisture = C.moisture THEN 1 ELSE 0 END
+ CASE WHEN P.surface = C.surface THEN 1 ELSE 0 END
+ CASE WHEN P.pack = C.pack THEN 1 ELSE 0 END
+ CASE WHEN P.ply = C.ply THEN 1 ELSE 0 END) DESC
) AS RowNum
FROM
@Product AS P
INNER JOIN
@PieceCount AS C
ON (P.specie = C.specie OR C.specie = 0)
AND (P.thick = C.thick OR C.thick = 0)
AND (P.grade = C.grade OR C.grade = 0)
AND (P.length = C.length OR C.length = 0)
AND (P.width = C.width OR C.width = 0)
AND (P.moisture = C.moisture OR C.moisture = 0)
AND (P.surface = C.surface OR C.surface = 0)
AND (P.pack = C.pack OR C.pack = 0)
AND (P.ply = C.ply OR C.ply = 0)
GROUP BY
P.Description,
C.PieceCount
) AS Temp
WHERE
RowNum = 1
Go to Top of Page

speno
Starting Member

18 Posts

Posted - 2008-03-12 : 09:34:56
Genius.. that did it. Thanks for your quick and insightful answer
Go to Top of Page
   

- Advertisement -