SQL - left join table to itself - sql

In short, want to left join table to itself, but only rows that have id 1 or 2
Table:
id f1
1 a
1 b
2 a
3 a
expected result
1 2 a a
1 2 b null
does not work:
select t1.id,t2.id, t1.f1,t2.f1
from table t1
left join table t2 on t1.f1 = t2.f1 and t1.id = 1 and t2.id = 2
Any idea ?

This construct is a bit strange, but you need to filter on the first table in where:
select t1.id, t2.id, t1.f1, t2.f1
from table t1 left join
table t2
on t1.f1 = t2.f1 and t2.id = 2
where t1.id = 1 ;
The general rule for a left join is that conditions on the first table go in the where clause. Conditions on the second table go in the on clause.

Related

SQL Hive - Replace null values with 0 (Hadoop Hive)

After conducting a left join, I was left with many null (empty) values. How may I replace those null values with a 0 in only certain columns within the same query?
select
m1.*, t2.Apple, t3.Berry, t4.Cherry
from
table1 as t1
left join table2 as t2 on t1.id = t2.id
left join table3 as t3 on t1.id = t3.id
left join table3 as t4 on t1.id = t4.id
;
Example Output
ID Apple Berry Cheery
1 1 NULL 1
2 1 NULL NULL
3 NULL 1 NULL
4 NULL NULL NULL
You can use coalesce() to replace null values with 0s:
select
t1.*,
coalesce(t2.Apple, 0) as apple,
coalesce(t3.Berry, 0) as berry,
coalesce(t4.Cherry, 0) as cherry
from
table1 as t1
left join table2 as t2 on t1.id = t2.id
left join table3 as t3 on t1.id = t3.id
left join table4 as t4 on t1.id = t4.id
;
Note that this assumes that all 3 fruit columns are of a numeric datatype.
Side note: I fixed a few typos on table aliases in your original query.

How to join a table with another one and then with itself on SQL Server 2017?

I have 2 tables where Table1 (t1) has the main data and Table2 (t2) has the relations between data.
I need a query to get data from table (t1) where condition is like
WHERE t1.row = 1 AND t1.code = s1
But this query started with (t1 left join t2 on t1.row = t2.row) and then produced answer will join on t1 again on t2.trow = t1.row.
Then answer must have some columns and rows which is shown in bottom.
Can you help me with this query?
I wrote this query :
SELECT
t1.code, t1_1.bed, t1_1.bes,
t2.t1row, t2.t2row
FROM
dbo.t1
LEFT OUTER JOIN
dbo.t2 ON t1.row = t2.t1row
LEFT OUTER JOIN
dbo.t1 t1_1 ON t2.t2row = t1_1.row
WHERE
t1.code = s1 And t1.row = '1'
But this query returns 2 rows where I need 5 rows!
I'm not sure why you want to link back to t1, since simply joining t1 with t2 produces the desired result. If you SELECT DISTINCT then two similar rows are replaced by one
SELECT DISTINCT
t1.row,
CASE WHEN trow=1 THEN 'OK' ELSE null END AS t2_row,
t1.bed, t1.bes, t1.code
FROM
t1
LEFT JOIN t2
ON t1.row = t2.frow
WHERE t1.code='s1'
ORDER BY t1.row;
Result:
row t2_row bed bes code
1 10000 s1
2 OK 7500 s1
3 OK 2500 s1
4 20000 s1
5 20000 s1
Use a CASE for t2.trow column and DISTINCT to remove duplicates
SELECT DISTINCT row,
CASE WHEN trow = 1 THEN 'OK'
ELSE ''
END as t2_row,
bed, bes, code
FROM t1
LEFT JOIN t2 ON t1.row = frow
AND code = 's1'
I am thinking that this does what you want:
select t1.*,
(case when exists (select 1
from t2
where t2.frow = t1.row and
t2.frow <> 1
)
then 'OK'
end)
from t1
where t1.code = 's1';

How to get first row value from third table while joining three tables

I'm new to mssql .Here am trying to get values from database by joining three tables .
Table 1:
Table 2 :
Here the image there is a possibility for a single user can have multiple image id form this I need to take any one of the image.
Table 3 :
Here am joining the Table 1 and Table 2 by using H_ID
and Table 2 and Table 3 by using IMG_ID.
What I want to do is Need to get all the colum values from Table 1 and Table 2 But the first URL from the Table 3.
In this case an employee has multiple images in the Table I need to take the 1 URL.
Result should be like this :
Query :
SELECT T1.H_ID AS 'ID',
T1.NAME,
T1.ROLE,
T2.SALARY,
T3.IMAGE
FROM TABLE1 T1
JOIN TABLE2 T2
ON T1.H_ID T2.H_ID
JOIN TABLE3 T3
ON T3.IMG_ID = T2.IMG_ID
WHERE T1.STATUS = 'ACTIVE'
Now this query returns 3 rows for the id H_ID = 1001 but It should be a single row.
Can anyone help me to fix this .
use row_number()
with cte as
(SELECT T1.H_ID AS 'ID',T1.NAME,T1.ROLE,T2.SALARY,T3.IMAGE
,row_number() over(partition by T2.img_id order by T3.id) rn
FROM TABLE1 T1
JOIN TABLE2 T2
ON T1.H_ID T2.H_ID
JOIN TABLE3 T3
ON T3.IMG_ID = T2.IMG_ID WHERE T1.STATUS = 'ACTIVE'
) select * from cte where rn=1
After you comments it seems you need subquery
select T1.*,T2.sal,a.url
FROM TABLE1 T1
JOIN TABLE2 T2
ON T1.H_ID T2.H_ID
left join ( select min(id),img_id,url from table3 group by img_id,url) a
on T2.IMG_ID= a.img_id
WHERE T1.STATUS = 'ACTIVE'
I think, You can simply use OUTER APPLY and TOP 1 for that
SELECT T1.H_ID AS 'ID',
T1.NAME,
T1.ROLE,
T2.SALARY,
T3.IMAGE
FROM TABLE1 T1
JOIN TABLE2 T2 ON T1.H_ID T2.H_ID
OUTER APPLY(SELECT TOP 1 T3.IMAGE
FROM TABLE3 T3 WHERE T3.IMG_ID = T2.IMG_ID
--ORDER BY <column_name> --to take top 1 value in specific order
) T3
WHERE T1.STATUS = 'ACTIVE'

Hive QL Except clause

How do I do an EXCEPT clause (like SQL) in Hive QL
I have 2 tables, and each table is a column of unique ids.
I want to find the list of ids that are only in table 1 but not in table 2
Table 1
apple
orange
pear
Table 2
apple
orange
In SQL you can do an EXCEPT clause (http://en.wikipedia.org/wiki/Set_operations_%28SQL%29) but you can't do that in Hive QL
I don't think there's any built-in way to do this but a LEFT OUTER JOIN should do the trick.
This selects all Ids from table1 that do not exist in table2:
SELECT t1.id FROM table1 t1 LEFT OUTER JOIN table2 t2 ON (t1.id=t2.id) WHERE t2.id IS NULL;
We can use NOT EXISTS clause in Hive as MINUS equivalent.
SELECT t1.id FROM t1 WHERE NOT EXISTS (SELECT 1 from t2 WHERE t2.id = t1.id);
1:
select distinct id from table1 where id not in (select distinct id from table2)
2:
select t1.id
from table1 as t1
left join table2 as t2
on t1.id = t2.id
where t2.id is null

Need help with Join Problem

I have 2 tables
Table 1
ID Status
1 D
2 F
3 D
Table 2
SID ID Approve
1 1 N
2 1 Y
3 1 Y
4 2 Y
5 3 Y
Result:- Should be
Table 1 (ID, Status)
3, D
2,F
Should not display 1 (As one of child rows have N in the Approve Column)
I need a query to joins 2 tables on ID and finds records that don not have N in their Approve column. Does anyone have any clue how to implement this?
I tried
SELECT * FROM Table1 AS t1
INNER JOIN Table2 AS t2
ON t2.id = t1.id
WHERE t2.Approve != 'N'
Doesn’t work
SELECT *
FROM Table1 t1
WHERE NOT EXISTS(SELECT * FROM Table2 t2 WHERE t2.ID = t1.ID AND t2.Approve = 'N')
More efficient and possibly easier to read is the following:
SELECT * FROM Table1 AS t1
LEFT JOIN Table2 AS t2
ON t2.id = t1.id
group by t1.id HAVING sum(t2.approve='Y') = count(t1.id)
Please Try
SELECT distinct t1.*
FROM Table1 AS t1
INNER JOIN Table2 AS tyes
ON tyes.id = t1.id
AND tyes.approve ='Y'
LEFT OUTER JOIN Table2 as tno
ON tno.id = t1.id
AND tno.approve ='N'
where tno.sid is null
It will select any line which is explicitely approved and never disapproved
Select * from table1 where id not in (select id from table2 where approve = 'N')
ID 1 is still returned since there is also a record in table 2 where approve = 'Y' for ID 1.
If you want to exclude any ID where approve is 'N' for any SID then you'll have to work with subqueries; roughly:
SELECT t1.ID,T1.Status FROM Table1 AS t1 INNER JOIN Table2 AS t2 ON t2.id = t1.id
where t1.id NOT IN (select id from Table2 where approve = 'N' and id = t1.id)
regards,
Stijn