Solved

Tricky Join SQL

Posted on 2011-02-10
9
440 Views
Last Modified: 2012-05-11
I've got a table of golfers that are in the 2011 US Masters.  One of the fields is qualification (how they managed to gain entrance to the tournament). I've got a table of the qualifications.  Golfers can qualify in one or more of 19 ways. So...

I need a join where all methods of qualification are returned

The tables look like this.
TblQual
QualID QualMethod
1 | Previous Winner
2 | Won British Open in last 5 years
3 | Won USOpen in last 5 years
4 | Won USPGA in last 5 years


TblPlayer
PlayerID Name Qual
1 | Lee Westwood | 1,3
2 | Ian Poulter | 2,3
3 | Martin Kaymer | 4
4 | Tiger Woods | 1,2,3,4

 
0
Comment
Question by:webdork
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 3
  • 2
  • 2
  • +1
9 Comments
 
LVL 22

Accepted Solution

by:
Thomasian earned 250 total points
ID: 34868246
Here's the query for you current table structure
DECLARE @TblQual table(QualID int, QualMethod varchar(100))
INSERT @TblQual
SELECT 1, 'Previous Winner'
UNION ALL SELECT 2, 'Won British Open in last 5 years'
UNION ALL SELECT 3, 'Won USOpen in last 5 years'
UNION ALL SELECT 4, 'Won USPGA in last 5 years'

DECLARE @TblPlayer table(PlayerID int, Name varchar(100), Qual varchar(100))
INSERT @TblPlayer
SELECT 1, 'Lee Westwood', '1,3'
UNION ALL SELECT 2, 'Ian Poulter', '2,3'
UNION ALL SELECT 3, 'Martin Kaymer', '4'
UNION ALL SELECT 4, 'Tiger Woods', '1,2,3,4'

SELECT *
FROM @TblPlayer P LEFT JOIN
     @TblQual Q ON ',' + P.Qual + ',' LIKE '%,' + CAST(Q.QualID as varchar) + ',%'

Open in new window



But I suggest that you add another table TblPlayerQual to join the 2 table.
DECLARE @TblQual table(QualID int, QualMethod varchar(100))
INSERT @TblQual
SELECT 1, 'Previous Winner'
UNION ALL SELECT 2, 'Won British Open in last 5 years'
UNION ALL SELECT 3, 'Won USOpen in last 5 years'
UNION ALL SELECT 4, 'Won USPGA in last 5 years'

DECLARE @TblPlayer table(PlayerID int, Name varchar(100))
INSERT @TblPlayer
SELECT 1, 'Lee Westwood'
UNION ALL SELECT 2, 'Ian Poulter'
UNION ALL SELECT 3, 'Martin Kaymer'
UNION ALL SELECT 4, 'Tiger Woods'

DECLARE @TblPlayerQual table(PlayerID int, QualID int)
INSERT @TblPlayerQual
SELECT 1,1
UNION ALL SELECT 1,2
UNION ALL SELECT 2,2
UNION ALL SELECT 3,3
UNION ALL SELECT 4,1
UNION ALL SELECT 4,2
UNION ALL SELECT 4,3
UNION ALL SELECT 4,4

SELECT *
FROM @TblPlayer P LEFT JOIN
     @TblPlayerQual PQ ON P.PlayerID=PQ.PlayerID LEFT JOIN
     @TblQual Q ON Q.QualID=PQ.QualID

Open in new window

0
 
LVL 41

Assisted Solution

by:Sharath
Sharath earned 250 total points
ID: 34868334
Not sure about your final result, but you can try like this to join both the tables.
select * 
  from (
SELECT PlayerID,Name,ltrim(SUBSTRING(Qual, n, CHARINDEX(',', Qual + ',',n) - n)) AS QualID
 FROM @TblPlayer
CROSS JOIN (SELECT number FROM master..spt_values WHERE type = 'P')  AS Numbers(n)
WHERE SUBSTRING(',' + Qual, n, 1) = ','
  AND n < LEN(Qual) + 1) t1
 join @TblQual t2 on t1.QualID = t2.QualID
order by t1.PlayerID

Open in new window


Check the result with your sample data.
declare @TblQual table(QualID int,QualMethod varchar(40))
insert @TblQual values (1,'Previous Winner')
insert @TblQual values (2 , 'Won British Open in last 5 years')
insert @TblQual values (3 , 'Won USOpen in last 5 years')
insert @TblQual values (4 , 'Won USPGA in last 5 years')


declare @TblPlayer table(PlayerID int,Name varchar(20),Qual varchar(20))
insert @TblPlayer values (1 , 'Lee Westwood' , '1,3')
insert @TblPlayer values (2 , 'Ian Poulter' , '2,3')
insert @TblPlayer values (3 , 'Martin Kaymer' , '4')
insert @TblPlayer values (4 , 'Tiger Woods' , '1,2,3,4')

select * 
  from (
SELECT PlayerID,Name,ltrim(SUBSTRING(Qual, n, CHARINDEX(',', Qual + ',',n) - n)) AS QualID
 FROM @TblPlayer
CROSS JOIN (SELECT number FROM master..spt_values WHERE type = 'P')  AS Numbers(n)
WHERE SUBSTRING(',' + Qual, n, 1) = ','
  AND n < LEN(Qual) + 1) t1
 join @TblQual t2 on t1.QualID = t2.QualID
order by t1.PlayerID
/*
PlayerID	Name	QualID	QualID	QualMethod
1	Lee Westwood	1	1	Previous Winner
1	Lee Westwood	3	3	Won USOpen in last 5 years
2	Ian Poulter	2	2	Won British Open in last 5 years
2	Ian Poulter	3	3	Won USOpen in last 5 years
3	Martin Kaymer	4	4	Won USPGA in last 5 years
4	Tiger Woods	1	1	Previous Winner
4	Tiger Woods	2	2	Won British Open in last 5 years
4	Tiger Woods	3	3	Won USOpen in last 5 years
4	Tiger Woods	4	4	Won USPGA in last 5 years
*/

Open in new window

0
 
LVL 5

Expert Comment

by:Abiel de Groot
ID: 34870623
I also think that there should be a thrid table which records the wins 'qual' with the players. the table could be as simple as this;

RecID - int (primary field)
PlayerId - int
Qual - tinyint

Each player could have either no entry or multiple entries.

This makes viewing and working with results very easy indeed.


Hope this helps.

A.
0
Instantly Create Instructional Tutorials

Contextual Guidance at the moment of need helps your employees adopt to new software or processes instantly. Boost knowledge retention and employee engagement step-by-step with one easy solution.

 
LVL 5

Expert Comment

by:Abiel de Groot
ID: 34870649
@Thomasian

I like your idea... quite complex, but complete.
0
 

Author Comment

by:webdork
ID: 34875524
I'm not really understanding... When I try the queries above I'm getting an error.

Syntax error converting the nvarchar value '6-B' to a column of data type int.

The column Qual in the Players Table is nvarchar because some of the qualifier codes are alpha and numeric like 6-B.

I thought it would be simpler and use the IN operator.

The results I'm looking for would be like this:

Select * from NewView where PlayerId = 4

Results:
Tiger Woods | (1) Former Masters Champion, (2) Winner of the Open Championship in the last 5 years, (r)  Winner of the US Open in the last 5 years.

etc..



0
 
LVL 41

Expert Comment

by:Sharath
ID: 34875652
>> I'm not really understanding... When I try the queries above I'm getting an error.
Which query are you referring?
>> The column Qual in the Players Table is nvarchar because some of the qualifier codes are alpha and numeric like 6-B.
I assumed that you have qualifiers separated by comma. Is that nit correct?
0
 

Author Comment

by:webdork
ID: 34875693
Yes quals separated by Comma. Query below.


select *
  from (
SELECT PlayerID,Name,ltrim(SUBSTRING(Qual, n, CHARINDEX(',', Qual + ',',n) - n)) AS QualID
 FROM @TblPlayer
CROSS JOIN (SELECT number FROM master..spt_values WHERE type = 'P')  AS Numbers(n)
WHERE SUBSTRING(',' + Qual, n, 1) = ','
  AND n < LEN(Qual) + 1) t1
 join @TblQual t2 on t1.QualID = t2.QualID
order by t1.PlayerID
0
 
LVL 22

Expert Comment

by:Thomasian
ID: 34876527
webdork,

Have you tried my suggestions in http:#a34868246 ?

If so, are you having the same error?
0
 
LVL 41

Expert Comment

by:Sharath
ID: 34877007
The what error are you getting? I have tested this for your sample data.
0

Featured Post

Announcing the Most Valuable Experts of 2016

MVEs are more concerned with the satisfaction of those they help than with the considerable points they can earn. They are the types of people you feel privileged to call colleagues. Join us in honoring this amazing group of Experts.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Why is this different from all of the other step by step guides?  Because I make a living as a DBA and not as a writer and I lived through this experience. Defining the name: When I talk to people they say different names on this subject stuff l…
Ever wondered why sometimes your SQL Server is slow or unresponsive with connections spiking up but by the time you go in, all is well? The following article will show you how to install and configure a SQL job that will send you email alerts includ…
Using examples as well as descriptions, and references to Books Online, show the documentation available for date manipulation functions and by using a select few of these functions, show how date based data can be manipulated with these functions.
Viewers will learn how the fundamental information of how to create a table.

623 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question