Join from multiple tables using WHERE IN - mysql

Im having a hard time finding anything on Google related to this problem.
What im trying to do is query from multiple tables with an unknown number of values using an IN statement like so...
SELECT * FROM table_1 t1 WHERE t1.t1_id IN ('12345223', '2343374') JOIN table_2 t2 WHERE t2.t2_id IN ('2164158194', '3232422423')
The code above demonstrates what I am trying to achieve. I'm not an SQL guru so im not entirely sure if what i'm going after can be accomplished this way or if there is a much better way to do it. Any help is much appreciated.

Update your query like this:
SELECT *
FROM table_1 t1
JOIN table_2 t2
ON t1.t1_id = t2.reft1_id
WHERE t1.t1_id IN ('12345223', '2343374')
AND t2.t2_id IN ('2164158194', '3232422423')
The "ON" clause will have to contain the two columns that are linked in the two tables.

You got the order of your clauses mixed up. You should go 1.)SELECT, 2.) FROM with JOINs, 3.) WHERE
Like this:
SELECT *
FROM table_1 t1
JOIN table_2 t2
WHERE t1.t1_id IN ('12345223', '2343374')
AND t2.t2_id IN ('2164158194', '3232422423')
But your statement also seems to miss a JOIN-condition so it will either result in an error (it does in oracle) or (assuming t1_id and t2_id are primary keys) give you 4 result lines (seems it does so in mysql):
t1_id t2_id
12345223 2164158194
12345223 3232422423
2343374 2164158194
2343374 3232422423
A JOIN without condition is almost never what you really want and if so it should be explicit in the statement and use CROSS JOIN.

Related

Query with CONCAT inside JOIN is slow

I need to get different values from 3 different tables (table1, table2, table3) where the common value is a reference number. This number appears on all 3 tables, except on table3 where the number is divided on three different columns. I tried to make a LEFT OUTER JOIN concatenating these three columns to make the whole reference number, but the query becomes significantly slower. This is the part of the query where the issue is found:
SELECT t1.type AS type, t2.client AS client, t3.somenumber AS somenumber, t4.anothernumber AS anothernumber
FROM table1 t1 JOIN table2 t2 ON t1.somevalue = t2.somevalue
JOIN table4 t4 ON t4.reference_number = t1.reference_number --Some validation I need to make on another table
--Here's the problem. table3's values 1 through 3 make the reference number found in the other tables.
--The CONCAT makes the query significantly slow.
LEFT OUTER JOIN table3 t3 ON CONCAT(t3.value1, t3.value2, t3.value3) = t1.reference_number
WHERE t1.date BETWEEN '2022-04-01' AND '2022-05-01'
AND t1.client IN ('client1', 'client2', 'client3', 'client4', 'client5')
GROUP BY t1.reference_number --Group by the reference number
I tried making a view to create a column where the reference number is 'stored', but it still takes a lot to run the query. Is there a way to optimize this?
Running on 10.3.32-MariaDB
The GROUP BY does not need CONCAT:
GROUP BY t3.value1, t3.value2, t3.value3
I don't understand why you tacked on t1.reference_number; it is either similar info or NULL. The NULL case might lead to extra groups, by it seems like a waste. (Add it on if necessary.)
Indexes:
t1: INDEX(date)
t1: INDEX(client, date)
t2: INDEX(somevalue, client)
t3: INDEX(value1, value2, value3)
t4: INDEX(reference_number)
Was t3.value a typo for t3.value3?
Consider getting rid of t4; you are not using any values from it. The only thing it is doing is to verify that table4 has a matching row.
What version of MySQL are you using?
It may be useful to have VIRTUAL or PERSISTENT (generated) column that is CONCAT (value1, value2, value3) and index it.
(And I agree with the Commenters that the "reference number" is ambiguous.)

Natural join works but not with all values

I can't understand whats happening...
I use two sql queries which do not return the same thing...
this one :
SELECT * FROM table1 t1 JOIN table1 t2 on t1.attribute1 = t2.attribute1
I get 10 rows
this other :
SELECT * FROM table1 NATURAL JOIN table1
I get 8 rows
With the NATURAL JOIN 2 rows aren't returned... I look for the missing lines and they are the same values ​​for the attribute1 column ...
It's impossible for me.
If anyone has an answer I could sleep better ^^
Best regards
Max
As was pointed out in the comments, the reason you are getting a different row count is that the natural join is connecting your self join using all columns. All columns are being compared because the same table appears on both sides of the join. To test this hypothesis, just check the column values from both tables, which should all match.
The moral of the story here is to avoid natural joins. Besides not being clear as to the join condition, the logic of the join could easily change should table structure change, e.g. if a new column gets added.
Follow the link below for a small demo which tried to reproduce your current results. In a table of 8 records, the natural join returns 8 records, whereas the inner join on one attribute returns 10 records due to some duplicate matching.
Demo
You need to 'project away' the attribute you don't want used in the join e.g. in a derived table (dt):
SELECT *
FROM table1
NATURAL JOIN ( SELECT attribute1 FROM table1 ) dt;

MySQL Easily Join Several Tables

All,
I have several tables, over 50, who have a common column "MYID" and can't figure out an easier way to join them without writing a gigantic query.
Imagine the following sample (only with 50 tables and 50 data points)
SELECT DATAPOINT1, DATAPOINT2, DATAPOINT3, DATAPOINT4, DATAPONT5
FROM TABLE1, TABLE2, TABLE3, TABLE4, TABLE5
WHERE TABLE1.MYID = TABLE2.MYID, MYTABLE2.MYID=MYTABLE3.MYID, MYTABLE4.MYID=MYTABLE5.MYID
How would I achieve the above results with a shorter query?
Looks like a horrible database design. The query you are showing is about what you need. Many, many tables to join, but that's the way it is with the design given. It cannot be shorter, because you need to list all the columns, all the tables and all criteria. There is nothing you can remove.
With proper join syntax:
select
t1.datapoint1,
t2.datapoint2,
t3.datapoint3,
...
from table1 t1
join table2 t2 on t2.myid = t1.myid
join table3 t3 on t3.myid = t1.myid
join ...
Very easy to generate with a programming language loop or Excel for instance.

MySQL - Same Data Problems

I apologise for the rushed posting.
The following are images of what I have:
Table 1 called 'players'
Table 2 called 'Reports'
And this is the format that I want the table to be displayed in:
I have tried using simple 'join' and 'and' statments and using some other's that I found on here. Still no avail.
Any help would be great.
Im not sure i understand, but i think that's is what you need:
SELECT `t2`.`id`,`t1`.`name` `Reported Name`, `t12`.`name` `Reporting Name`
FROM `test`.`Reports` `t2`
JOIN `test`.`players` `t1`
on `t1`.`id`=`t2`.`reported_uid`
join `test`.`players` `t12`
on `t12`.`id`=`t2`.`reporting_uid`;
http://sqlfiddle.com/#!2/360d2/1/0
I agree with #Ohah that it's a little unclear, but I'll take a shot at it. If you're just trying to show all of Table 2 with one of the name fields from Table 1, you could do it this way:
SELECT t1.Example_Name, t2.*
FROM
Table_2 t2
JOIN Table_1 t1 ON t1.Name_1 = t2.User_Reported
Table 1 = t1 (t1 is an alias to Table 1 so you don't have to type the whole name out)
Table 2 = t2 (t2 is an alias to Table 2)
"Example_Name" is whichever field you want from the first table
The main question is how the two tables are related and what data you want to get from each. But I hope this helps.

What is better way to join in mysql?

I wanted to join 3 or more tables
table1 - 1 thousand record
table2 - 100 thousands record
table3 - 10 millions record
Which of the following is best(speed wise performance):-
Note: pk and fk are primary and foreign key for respective tables and FILTER_CONDITION1 and FILTER_CONDITION2 are respective restricting records query normally found in where
Case 1 :taking smaller tables first and joining larger one later
Select table1.*,table2.*,table3.*
from table1
join table2
on table1.fk = table2.pk and FILTER_CONDITION1
join table3
on table2.fk = table3.pk and FILTER_CONDITION2
Case 2
Select table1.*,table2.*,table3.*
from table3
join table2
on table2.fk = table3.pk and FILTER_CONDITION2
join table1
on table1.fk = table2.pk and FILTER_CONDITION1
Case 3
Select table1.*,table2.*,table3.*
from table3
join table2
on table2.fk = table3.pk
join table1
on table1.fk = table2.pk
where FILTER_CONDITION1 and FILTER_CONDITION2
The cases you show are equivalent. What you are describing is in the end the same query and will be seen by the database as such: the database will make a query plan.
The best thing you can do is use EXPLAIN and check out what your query actually does: this way you can see they will probably be run the same, AND if there might be a bottle neck in there.
As #Nanne updated in his answer that normally mysql do it its own (right ordering) but some time (rare case) mysql can read table join in wrong order and can kill query performance in this case you can follow below approach-
If you can filter data from your bulky tables like table2 and table3 (suppose you can get only 500 records after joining these tables and applying filter) then first you filter your data and then you can join that filtered data with your small table..in this way you can get performance but there can be various combinations, so you have to check by which join you can do more filteration..yes explain will help you to know it and index will help you to get filtered data.
After above approach you can say mysql to use ordering as you have in your query by syntax "SELECT STRAIGHT_JOIN....." same as some time mysql does not use proper index and we have to use force index