简体   繁体   中英

mysql create view of two tables based on id from third

I have found a lot of similar posts about merging two tables based on an id from a third, however I just can't seem to work out the logic.

Give the three tables

tableA

| uuid |  ttl  |  ord |
-----------------------
| alpha|  Alp  |     1|
| beta|  Bet  |     2|
| gamma|  Gam  |     3|

tableB

| uuid |  ttl  |  ord | tab_A_ref
--------------------------------
| joe  |  Jo  |     1|  alpha
| mike |  Mi  |     2|  beta
| peter|  Pe  |     3|  alpha
| alan |  Pe  |     4|  beta
| tom  |  Pe  |     5|  gamma

tableC

| uuid |  ttl  |  ord | tab_A_ref
--------------------------------
| jane  |  Ja  |     1|  alpha
| marg  |  Ma  |     2|  beta
| phobe |  Ph  |     3|  alpha
| anon  |  An  |     4|  beta
| toni  |  To  |     5|  gamma

I am looking to create a view myView where tab_A_ref = alpha or beta

| uuid  |  ttl  | ord | tab_A_ref
| joe   |  Jo   |     1|  alpha
| peter |  Pe   |     3|  alpha
| jane  |  Ja   |     1|  alpha
| phobe |  Ph   |     3|  alpha
| mike  |  Mi   |     2|  beta
| alan  |  Pe   |     4|  beta
| marg  |  Ma   |     2|  beta
| anon  |  An   |     4|  beta

using the a basic join,

SELECT
  tableB.uuid, tableB.ttl, tableB.ord, tableB.tab_A_ref  
  FROM tableB
  INNER JOIN tableA on tableB.tab_A_ref = tableA.uuid 

I extended the logic to merge the two

SELECT
      tableB.uuid, tableB.ttl, tableB.ord, tableB.tab_A_ref,
      tableC.uuid, tableC.ttl, tableC.ord, tableC.tab_A_ref,  
FROM 
      tableB INNER JOIN tableA on tableB.tab_A_ref = tableA.uuid, 
      tableC INNER JOIN tableA on tableC.tab_A_ref = tableA.uuid

but that generates an error not unique table/alias: tableA

From the other posts it looks like I should have a nested bracketed JOIN, having tried a number of combinations all fail. So how do I format the second JOIN ?

All tables (temporary, subqueries, physical or otherwise) must be uniquely named in the query.

Otherwise the database engine has no idea which source of data you're referring to.

Your original:

SELECT
      tableB.uuid, tableB.ttl, tableB.ord, tableB.tab_A_ref,
      tableC.uuid, tableC.ttl, tableC.ord, tableC.tab_A_ref,  
FROM 
      tableB INNER JOIN tableA on tableB.tab_A_ref = tableA.uuid, 
      tableC INNER JOIN tableA on tableC.tab_A_ref = tableA.uuid

In the above, how does the query engine know which tableA to use? You've declared it twice. Remember you're applying a filter ( ON tableB.tab_A_ref = tableA.uuid ) - so you've got two result-sets (one from the first join, a different one from the second) and they're both referred to as tableA .

Simply, use an alias ( AS ) to uniquely reference all tables (joined or otherwise):

SELECT
      tableB.uuid, tableB.ttl, tableB.ord, tableB.tab_A_ref,
      tableC.uuid, tableC.ttl, tableC.ord, tableC.tab_A_ref,  
FROM 
      tableB INNER JOIN tableA AS a_ref ON tableB.tab_A_ref = a_ref.uuid, 
      tableC INNER JOIN tableA AS b_ref ON tableC.tab_A_ref = b_ref.uuid

The following JOIN logic is incorrect:

  tableB INNER JOIN tableA on tableB.tab_A_ref = tableA.uuid, 
  tableC INNER JOIN tableA on tableC.tab_A_ref = tableA.uuid

The query should be:

SELECT
    tableB.uuid, tableB.ttl, tableB.ord, tableB.tab_A_ref  
FROM tableB
    INNER JOIN tableA 
            ON tableB.tab_A_ref = tableA.uuid 
    INNER JOIN tableC 
            ON tableC.tab_A_ref = tableA.uuid 


The essence of the logic used here is that the first JOIN already creates a virtual unit that can be joined with any other tables as necessary. tableA is already partaking in that JOIN and unless there's some special need (which doesn't seem to be the case here), you don't need to specify it again in the query.

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