0

When I try to join the below two table I am not able to get the output I want by the join. I tried using join but it didn't work let me know if its possible with plsql

Table 1:          
col1 col2          
1    a                    
1    b                 
1    c                    
2    a                    
2    b                    
3    a                    

table 2:

col1  col2

1     x 

1     y

2     x

2     y

3     x

3     y

The output must be:

col1 col2 col3

1      a    x

1      b    y

1      c    

2      a    x

2      b    y

3      a    x

3           y    

If use the join I am not able to get the same output as above. The output I am getting is

1  a x

1  a y

1  b x

1  b y

1  c x 

1  c y

2  a x

.....
.....

3  a x

3  a y
Jon Heller
  • 34,999
  • 6
  • 74
  • 132

2 Answers2

1

What you are searching is called a FULL OUTER JOIN. The result of this join contains elements from both input-tables, matching records get combined.

You can find more information here: https://stackoverflow.com/questions/4796872/full-outer-join-in-mysql

Community
  • 1
  • 1
Benvorth
  • 7,416
  • 8
  • 49
  • 70
  • Even the Full outer join is giving the same output as the above. The row here are not unique as the example you mentioned – Rajagopal Vajja Aug 12 '15 at 20:06
  • In your desired output you switch the join-logic: you can't have both `1 c null` and `3 null y`. Please review your question and tell us by what logic you want the output created. – Benvorth Aug 13 '15 at 06:25
  • Can we join them using PLSQL or any other method? I have a similar problem for the combining 2 table which are pretty much similar as above. – Rajagopal Vajja Aug 13 '15 at 16:02
  • Please let me know if you could get the above output as mentioned not the one as the one I got – Rajagopal Vajja Aug 21 '15 at 18:33
0

Using Window functions, specifically ROW_NUMBER() and partitioning by the Col1 in both tables, we can get a partitioned row_number that can be used as part of the join.

In other words, it seems to me that the order that the records are in is crucial for the join and result set you are desiring. Furthermore, using @Benvorth's suggestion of a FULL OUTER JOIN to achieve the NULLs in both direction.. I believe this might work:

SELECT
    COALESCE(t1.col1,t2.col1) as col1,
    t1.col2,
    t2.col2
FROM
    (SELECT col1, col2, ROW_NUMBER() OVER (PARTITION BY col1 ORDER BY col2 ASC) as col1_row_number FROM table1) t1
    FULL OUTER JOIN
    (SELECT col1, col2, ROW_NUMBER() OVER (PARTITION BY col1 ORDER BY col2 ASC) as col1_row_number FROM table2) t2 ON
        t1.col1 = t2.col1 AND
        t1.col1_row_number = t2.col1_row_number

That ROW_NUMBER() OVER (PARTITION BY col1, ORDER BY col2 ASC) bit will create row number for each record. The row_number will restart back at 1 for each new col1 value encountered. You can think of it like a RANK for each distinct Col1 value based on Col2's value. Table1's output from the subquery SELECT col1, col2, ROW_NUMBER() OVER (PARTITION BY col1 ORDER BY col2 ASC) as col1_row_number FROM table1 will look like:

Table 1:          
col1 col2 col1_row_number        
1    a     1               
1    b     2            
1    c     3               
2    a     1               
2    b     2               
3    a     1

So we do that with both tables, then we use that row number as part of the join along with col1.

A sqlfiddle showing this matching your desired result from the question

JNevill
  • 46,980
  • 4
  • 38
  • 63
  • I have done that as my friend suggested it has many values missing if have row number and col doesn't match. The third row from expected output misses and once the row order fails the complete sequence fails. Thanks for the information. – Rajagopal Vajja Aug 21 '15 at 18:47
  • I have added your exact example and this query to a sqlfiddle and got the exact resultset you are looking for. If this doesn't satisfy your question, then you need to update your question. http://sqlfiddle.com/#!15/a1f1d/1 – JNevill Aug 21 '15 at 18:52
  • I will try again and let you know in few minutes – Rajagopal Vajja Aug 21 '15 at 18:53
  • Every thing works but the last row for 3 null y the col1 value is missing the number 3 is missing – Rajagopal Vajja Aug 21 '15 at 19:05
  • In that case, use `COALESCE(t1.col1, t2.col1)` in the `SELECT` of the main query. I will edit the answer to show that. – JNevill Aug 21 '15 at 19:10
  • Thanks a lot for the info – Rajagopal Vajja Aug 21 '15 at 19:32