Join tables with different data in rows - sql

I have two tables like this
t1
id value1
BMC 16
EC 22
LLU 60
MC 274
UHC 54
UHS 28
t2
id value2
BMC 5
e900 4
EC 7
LLU 2
MC 1
How could I get this out put using sql server? I have used full outer join also. But its not gives me correct results
BMC 16 5
EC 22 7
LLU 60 2
MC 274 1
UHC 54
UHS 28
e900 4
Here is my outer join, Its for two select statements. Not for tables. But those select statements gives above results (t1, t2)
SELECT * FROM
(
SELECT b.EntityCode, COUNT('a') AS GroupCountUser1 FROM #TempUser a INNER JOIN OP_TB_TRN_Entity b
ON a.Entity=b.EntityID
GROUP BY b.EntityCode
) t1
FULL OUTER JOIN
(SELECT b.EntityCode, COUNT('a') AS GroupCountUser2 FROM #TempUser1 a INNER JOIN OP_TB_TRN_Entity b
ON a.Entity=b.EntityID
GROUP BY b.EntityCode) t2
ON t1.EntityCode = t2.EntityCode

Guessing you are forgetting to coalesce the IDs, try
Select coalesce( A.Id, B.Id) id,
A.Value1, B.Value2
From A Full Join B On A.Id = B.Id

Select concat( t1.value1, t2.value2) as totalvalue
From t1 join t2 where t1.Id = t2.Id
If i understand what you're asking, this should help.

Related

Sql query to get join of two tables and both table has where query

Stuck at join, tried left, right, left outer , right outer joins
table 1
selectionID name type
1 abc 1
2 def 1
3 ghi 2
4 dhi 2
5 gki 2
6 ppp 2
Table 2
TID UserID selectionID isOK
1 10 3 0
2 19 3 0
3 10 8 0
6 10 5 1
Desired result is
join of
select from table 1 where type =2
select from table 2 where UserID = 10
selectionID name type TID userID
3 ghi 2 1 10
4 dhi 2 undefined undefined/null
5 gki 2 undefined undefined/null
6 ppp 2 6 10
so basically i want all data from table 1 that fits in where clause and their respective data in table 2 with another where clause
As long as i have done research i need to use inner query of second table...am I going right way?
Try the following query:
SELECT t1.selectionID, t1.name, t1.type, t2.tid, t2.userID
FROM table1 t1 LEFT JOIN table2 t2 ON t1.type = t2.TID AND t2.userID = 10
WHERE t1.type = 2;
Stuck at join, tried left, right, left outer , right outer joins ... well LEFT JOIN is same as LEFT OUTER JOIN. BTW, you are looking for a LEFT JOIN probably like
select t1.selectionID,
t1.name,
t1.type,
t2.TID,
t2.UserId
from table1 t1
left join table2 t2 on t1.selectionID = t2.selectionID
and t2.UserId = 10
where t1.type = 2;
You were probably failing because placing the conditions in the where clause. If a row doesn't join you will have nulls in its columns, so a where condition will discard those rows
select *
from table1 t1
left join
table2 t2
on t1.selectionID = t2.selectionID and
t2.userID = 10
where t1.type = 2
Another way, is to force nulled rows to be accepted, using coalesce
select *
from table1 t1
left join
table2 t2
on t1.selectionID = t2.selectionID and
where t1.type = 2 and
coalesce(t2.userID, 10) = 10
select * from table1 t1
left join table2 t2 ON t1.SelectionID = t2.SelectionID
where t1.type = 2 AND t2.UserID = 10

Sql oracle left join only match single rows

I need short sql to left join T2 on T1 only if single math
T1 T2 Desired
F1 F2 F1 F2 F1 F2
1 A A RR 1
2 B A 2 UU
3 C A TT 3
4 D B UU 4 YY
5 E C VV 5 ZZ
C XX
D YY
E ZZ
You could use a simple GROUP BY/COUNT to count the rows per hit and a CASE expression to only output the value if the row count is <=1;
SELECT T1.F1, CASE WHEN COUNT(*)>1 THEN NULL ELSE MAX(T2.F2) END F2
FROM T1
LEFT JOIN T2 ON T1.F2 = T2.F1
GROUP BY T1.F1
An SQLfiddle to test with.
USING group by to eliminate the records with duplicates and doing left join to get all values from T1
select T1.F1, ISNULL(T2.F2,'') from T1
LEFT JOIN
(
select F1 from T2
group by F1
having count(*) =1
) T
on T1.F1 = T.F1
LEFT JOIN T2
on T2.F1 = T.F1

Joining multiple tables into one under one Id

I have dozen of tables with following format:
Table 1
[idA] [numA]
NULL 8
1 10
2 15
3 16
Table 2
[idB] [numB]
2 14
3 30
4 32
Table 3
[idC] [numC]
NULL 56
1 24
4 37
5 36
...
Now, I'm not sure how to formulate T-Sql query in order to produce following result:
[id] [numA] [numB] [numC] ...
NULL 8 0 56
1 10 0 24
2 15 14 0
3 16 30 0
4 0 32 37
5 0 0 36
Are there any suggestions on how to solve this?
I offer a solution with the full outer join, because that seems like the natural approach:
SELECT coalesce(a.id, b.id, c.id, . . .) as id,
a.NumA, b.NumB, c.NumC, . . .
FROM TableA a full outer join
TableB b
on a.id = b.id full outer join
TableC c
on coalesce(a.id, b.id) = c.id
However, the query needs to be written carefully, to keep the coalesces in line. The one advantage of this approach is that it should use indexes on the id columns for the query.
please try this
select id, max(numa),max(numb),max(numc) from
(
select id,numa,0 as numb,0 as numc from tb1
union all
select id,0 as numa,numb as numb,0 as numc from tb2
union all
select id,0 as numa,0 as numb,numc as numc from tb3
)X
group by id
order by id
Thanks
Rajath
SELECT Maintable.id,
Table1.numA,
Table2.numB,
Table3.numC
FROM (SELECT ida AS id
FROM Table1
UNION
SELECT idb AS id
FROM Table2
UNION
SELECT idc AS id
FROM Table3) MainTable
LEFT JOIN Table1
ON Maintable.id = Table1.Ida
LEFT JOIN Table2
ON Maintable.id = Table2.idB
LEFT JOIN Table3
ON Maintable.id = Table3.idC

Getting top row for each unique group in the inner joined group query

table 1
id name class
1 ab A
2 cd A
3 ef B
4 ab B
5 cd B
table 2
name test marks
ab 1 90
ab 2 70
cd 2 80
cd 3 85
ef 3 85
ef 4 60
Hi, I have 2 tables above, my question is what is the most efficient/best or simplest way to get the highest marks from table 2 for each person and join to table 1 such that returns:
id name class [highest marks]
1 ab A 90
2 cd A 85
3 ef B 85
Assuming SQL Server 2005+, using analytic/ranking/windowing functionality:
WITH example AS (
SELECT a.id,
a.name,
a.class,
b.marks,
ROW_NUMBER() OVER(PARTITION BY a.id
ORDER BY b.marks DESC) AS rank
FROM TABLE_1 a
JOIN TABLE_2 b ON b.name = a.name)
SELECT e.id,
e.name,
e.class,
e.marks
FROM example e
WHERE e.rank = 1
Using aggregates:
SELECT a.id,
a.name,
a.class,
b.marks
FROM TABLE_1 a
JOIN (SELECT t.name,
MAX(t.mark) AS max_mark
FROM TABLE_2
GROUP BY t.name) b ON b.name = a.name
Another option if you dont want to use CTE (Common Table Expressions)
SELECT table1.id, table1.name, table1.class, MAX(table2.marks) AS [highest marks]
FROM table1 INNER JOIN
table2 ON table1.name = table2.name
GROUP BY table1.id, table1.name, table1.class

SQL Query to sum fields from different tables

I'm a humble programmer that hates SQL ... :) Please help me with this query.
I have 4 tables, for example:
Table A:
Id Total
1 100
2 200
3 500
Table B
ExtId Amount
1 10
1 20
1 13
2 12
2 43
3 43
3 22
Table C
ExtId Amount
1 10
1 20
1 13
2 12
2 43
3 43
3 22
Table D
ExtId Amount
1 10
1 20
1 13
2 12
2 43
3 43
3 22
I need to make a SELECT that shows the Id, the Total and the SUM of the Amount fields of tables B, C and D like this
Id Total AmountB AmountC AmountD
1 100 43 43 43
2 200 55 55 55
3 500 65 65 65
I've tried with a inner join of the three tables by the Id and doing a sum of the amount fields but results are not rigth. Here is the wrong query:
SELECT dbo.A.Id, dbo.A.Total, SUM(dbo.B.Amount) AS Expr1, SUM(dbo.C.Amount) AS Expr2, SUM(dbo.D.Amount) AS Expr3
FROM dbo.A INNER JOIN
dbo.B ON dbo.A.Id = dbo.B.ExtId INNER JOIN
dbo.C ON dbo.A.Id = dbo.C.ExtId INNER JOIN
dbo.D ON dbo.A.Id = dbo.D.ExtId
GROUP BY dbo.A.Id, dbo.A.Total
Thanks in advance, its just that I hate SQL (or that SQL hates me).
EDIT: I had a typo. This query is not giving the right results. Extended the example.
Or you can take advantage of using SubQueries:
select A.ID, A.Total, b.SB as AmountB, c.SC as AmountC, d.SD as AmountD
from A
inner join (select ExtID, sum(Amount) as SB from B group by ExtID) b on A.ID = b.ExtID
inner join (select ExtID, sum(Amount) as SC from C group by ExtID) c on c.ExtID = A.ID
inner join (select ExtID, sum(Amount) as SD from D group by ExtID) d on d.ExtID = A.ID
From your description, this query should give you an error as you are using the non-existent column dbo.A.Amount in your group by. Changing this to dbo.A.Total might be what you need.
If you need all the amounts together, then try this query:
select A.Id, A.Total, sum(B.Amount + C.Amount + D.Amount) AS Total_Amount
from A
inner join B on A.Id = B.ExtId
inner join C on A.Id = C.ExtId
inner join D on A.Id = D.ExtId
group by A.Id, A.Total;
This one also works well
SELECT (SELECT SUM(Amount) FROM TableA) AS AmountA,
(SELECT SUM(Amount) FROM TableB) AS AmountB,
(SELECT SUM(Amount) FROM TableC) AS AmountC,
(SELECT SUM(Amount) FROM TableD) AS AmountD
This might help other users.
SELECT Total=(Select Sum(Amount) from table a)+(Select Sum(Amount) from table b)+(Select Sum(Amount) from table c)
Try this code
SELECT Total=isnull((Select Sum(Isnull(Amount,0)) from table a),0)+isnull((Select Sum(isnull(Amount,0)) from table b),0)+isnull((Select Sum(isnull(Amount,0)) from table c),0)