I have to tables: user and userimages.
Right now, I'm using the following query:
SELECT * FROM users u INNER JOIN userimages ui ON u.id=ui.userid;
Yes. It retrieved the records if the userid and id is equal. What I really want to do is to select all records from table users even if its id is not present on the second table (userimages)
My question is how to select all records in the users table with or withou userid on the second table?
You're looking for a LEFT JOIN, which will pull all rows from the first table and join where applicable to the right.
SELECT * FROM users u LEFT JOIN userimages ui ON u.id=ui.userid;
Related
I have a products table where I include 3 columns, created_user_id, updated_user_id and in_charge_user_id, all of which are related to my user table, where I store the id and name of the users.
I want to build an efficient query to obtain the names of the corresponding user_id's.
The query that I build so far is the following:
SELECT products.*,
(SELECT name FROM user WHERE user_id = products.created_user_id) as created_user,
(SELECT name FROM user WHERE user_id = products.updated_user_id) as updated_user,
(SELECT name FROM user WHERE user_id = products.in_charge_user_id) as in_charge_user
FROM products
The problem with this query is that if I have 30,000 records, I am executing 3 more queries per row.
What would be a more efficient way of achieving this? I am using mysql.
For each type of user id (created, updated, in_charge) you would JOIN the users table once:
SELECT
products.*,
u1.username AS created_username,
u2.username AS updated_username,,
u3.username AS in_charge_username,
FROM products
JOIN user u1 ON products.created_user_id = u1.user_id
JOIN user u2 ON products.updated_user_id = u2.user_id
LEFT JOIN user u3 ON products.in_charge_user_id = u3.user_id
This is the best practice method to obtain the data.
It is similiar to your query with sub-selects but a more modern approach which I think the database can optimize and utilize better.
Important:
You need foreign key index on all the user_id fields in both tables!
Then the query will be very fast no matter how many rows are in the table. This requires an engine which supports foreign keys, like InnoDB.
LEFT JOIN or INNER JOIN ?
As the other answers suggest a LEFT JOIN, I would not do a left join.
If you have an user id in the products table, there MUST be a linked user_id in the user table, except for the in_charge_user which is only present some times. If not, the data would be semantically corrupt. The foreign keys assure that you always have a linked user_id and a user_id can only be deleted when there is no linked product left.
JOIN is equivalent to INNER JOIN.
You can use LEFT JOIN instead of subselects.
Your query should be like:
SELECT
P.*,
[CU].[name],
[UU].[name],
[CU].[name]
FROM products AS [P]
LEFT JOIN user AS [CU] ON [CU].[user_id] = [P].[created_user_id]
LEFT JOIN user AS [UU] ON [UU].[user_id] = [P].[updated_user_id]
LEFT JOIN user AS [CU] ON [CU].[user_id] = [P].[in_charge_user_id]
First, your query should be fine. You only need an index on user(user_id) or better yet user(user_id, name) for performance. I imagine that the first exists.
Second, you can write this using LEFT JOIN:
SELECT p.*, uc.name as created_user,
uu.name as updated_user, uin.name as in_charge_user
FROM products p LEFT JOIN
user uc
ON uc.user_id = p.created_user_id LEFT JOIN
user uu
ON uu.user_id = p.updated_user_id LEFT JOIN
user uin
ON uin.user_id = p.in_charge_user_id;
With one of the above indexes, the two methods should have very similar performance.
Also note the use of LEFT JOIN. This handles the case where one or more of the user ids is missing.
Try this below query
SELECT products.*, c.name as created_user,u.name as updated_user,i.name as in_charge_user
FROM products left join user c on(products.created_user_id=c.user_id ) left join user u on(products.updated_user_id=u.user_id ) left join user u on(products.in_charge_user_id=i.user_id )
Also as Gordon Linoff mentioned create index on user table will fetch your data faster.
I need to find out how to pull user names into a VIEW from a different table. I have 3 tables, User, Lead, and Lead_detail. In the users table there is an ID field which is stored in the Created_By field in the Lead table. In the Lead table I have an ID field that is stored in the Lead_detail Lead_ID field.
I have created a VIEW to the Lead_detail table which pulls all the info I need but I have found that I don't have the users name in that VIEW so I need to ALTER my view to add in the users names per lead but I am having trouble with the statement.
Before altering the VIEW I wanted to try a SELECT statement to see if I get any data,
SELECT * FROM Lead_detail
JOIN Lead
ON Lead_detail.lead_id = Lead.id
WHERE Lead.Created_by = Users.ID
But this didn't work. What would be a correct statement so that I can pull the users names into the Lead VIEW?
I think you missed a join to the Users table:
SELECT
*
FROM
Lead_detail
INNER JOIN Lead
ON Lead_detail.lead_id = Lead.id
INNER JOIN Users
ON Lead.Created_by = Users.ID
I have a query that I would like to run but is not returning the expected results.
So my tables are like this
users (has two columns)
user_id,name
users_archive (has the same two columns)
user_id,name
I want to basically run a query that lists user_id from the respective table where the username matches what I'm searching for
For my example I have a user called MikeBOSS in users_archive with an user_id of 123 (there is no MikeBOSS in users table)
SELECT users.user_id, users_archive.user_id
FROM users
LEFT JOIN users_archive ON users_archive.name='MikeBOSS'
WHERE users.name='MikeBOSS';
but that returns no results
SELECT users.user_id, users_archive.user_id
FROM users, users_archive
WHERE (users.name='MikeBOSS' OR users_archive.name='MikeBOSS');
That returns a bunch of results from the users table that are incorrect.
Could someone maybe point me in the correct direction?
You do not want a JOIN, you want a UNION. Look
SELECT users.user_id, 'users'
FROM users
WHERE users.name='MikeBOSS'
UNION
SELECT users_archive.user_id, 'archive'
FROM users_archive
WHERE users_archive.name='MikeBOSS';
A join condition normally links two tables. Yours does not:
ON users_archive.name='MikeBOSS'
A join condition that does link the two tables might look something like:
ON users.name = users_archive.name
If you wonder about the number of rows this returns, check each table individually. Is there even a row with name = 'MikeBoss' in the users_archive table?
Change
SELECT users.user_id, users_archive.user_id
FROM users
LEFT JOIN users_archive ON users_archive.name='MikeBOSS'
WHERE users.name='MikeBOSS';
To
SELECT users.user_id, users_archive.user_id
FROM users
LEFT JOIN users_archive ON users.name = users_archive.name WHERE users.name='MikeBOSS';
May be this could work if you have no relation between 2 tables. Using left join gives you record from one table even if its not present in other.
SELECT users.user_id, users_archive.user_id
FROM users
LEFT JOIN users_archive ON users.userid = users_archive.userid and users.name = users_archive.name
WHERE users.name='MikeBOSS';
I have two tables and they are as follows:
USERS
ORDERS
I want select all users who have at least 1 order or more in the ORDERS table. I know there is an inline query for this in MySQL, but right now I have to select all users and then make another query seeing if each user has an order - all this using a PHP loop.
What I am doing now is not ethically correct, so I basically just want to select all users who have been referenced in the ORDERS table in ONE MySQL query.
This is a query you should be using
select distinct u.* from users u
inner join orders o on o.user_id = u.id;
Note the distinct and u.*. This query will not select fields from orders and it will not select the same user twice (if one has more than one order).
Demo: http://sqlfiddle.com/#!2/6ebcc/3
You can use mysql join syntax. Assuming both of your tables has userid column, this is the example :
SELECT * FROM USERS a JOIN ORDERS b ON
a.UserId = b.UserId
This is a simple database operation, see here for the explanation join
I have to tables that I want to get all the results of both connect by a common cell. The problems is the second table only has some of records of the first table.
Table 1 forms
form_id, description, image,dept
Table 2 records
record_id, form_id, comments, added_date, done_date
If do a query like this:
SELECT * FROM form
JOIN records ON record.form_id = form.form_id
I do not get all of the forms because there is no record for that form. Is there away to do something like this? I would create a blank record for each form on in the records table, but I could not figure that out either.
This is a perfect application for a LEFT OUTER JOIN.
Example:
SELECT f.*, r.*
FROM form f
LEFT JOIN records r
ON r.form_id = f.form_id
ORDER BY f.description, r.added_date;
Use left join for these cases
SELECT * FROM form
LEFT JOIN records ON record.form_id = form.form_id
Please check which one u need --
LEFT OUTER JOIN :
Will include all records from Table Mentioned in Left Side and Matched Records from Right Side table, unmached record will be null
Ex :
SELECT *
FROM forms
LEFT JOIN records ON forms.form_id = record.form_id
FULL OUTER JOIN:
Will include all data from both table and unmatched will be null
Ex :
SELECT *
FROM forms
FULL OUTER JOIN records ON forms.form_id = record.form_id