Mysql - Show unrelated results between two tables from table 1 - sql

I have to 2 tables:
table A:
pid|filename|date
-----------------
1 |file1 |2009
2 |file2 |2009
3 |file3 |2009
4 |file4 |2009
table B:
pid|filename
------------
1 |filex1
1 |filex2
2 |filex3
2 |filex4
the result I want to get is:
pid|filename|date
-----------------
3 |file3 |2009
4 |file4 |2009
thats mean it should show me only the rows of table A that don't have a relation with the second table.
I started with this code, but it did not work!
$do_q=mysql_query("SELECT *
FROM A LEFT JOIN B
ON (A.pid <> B.pid)");
while($row = mysql_fetch_array($do_q)){
echo $row['pid'];
echo $row['filename'];
echo $row['date'];
}
Thank you.

SELECT A.*
FROM A
LEFT JOIN B
ON A.pid = B.pid
WHERE b.pid IS NULL

I think this should work for you:
SELECT *
FROM A
WHERE pid NOT IN (SELECT pid from B)

SELECT
*
FROM tableA A
WHERE(NOT EXISTS(SELECT 1 FROM tableB B WHERE B.pid = A.pid))

Related

how to execute query for each row result of another query

I have 2 tables , one stores IDs and another logs for each ID , i would like to get sum of log for each ID and ID number from these 2 tables
A B
------- -------------
ID ID_C LOG
1 1 15
2 1 30
3 4 44
4 2 14
5 3 88
3 10
2 10
for getting sum query is
SELECT SUM(LOG) FROM B WHERE ID_C ='2' ;
notice ID and ID_C are same but name is different in tables
and for getting all ids available query is
SELECT ID FROM A ;
I would like to get the following table result
result
--------------------
ID SUM
1 45
4 44
2 24
3 98
I tried
SELECT SUM(LOG) FROM B WHERE ID_C in (SELECT ID FROM A ) ;
but it result in sum of all IDs
It looks like you just need a join aggregation here:
SELECT a.ID, SUM(b.LOG) AS SUM
FROM A a
INNER JOIN B b
ON b.ID_C = a.ID
GROUP BY a.ID
ORDER BY a.ID;
Note that the inner join will also remove ID values from the A table which no entries whatsoever in the B table, which seems to be the behavior you want.
you should use inner join and GROUP BY:
SELECT A.ID as ID, SUM(LOG) AS SumLOG
FROM A inner join B ON A.ID = B.ID_C
GROUP BY A.ID
if you needed can use where for ID filter.

How to identify non-existing keys with reference to a table that has all mandatory keys, SQL?

I have the table 'Table01' which contains the keys that should be mandatory:
id
1
2
3
4
And I also have the table 'Table02' which contains the records to be filtered:
id
customer
weight
1
a
100
2
a
300
3
a
200
4
a
45
1
b
20
2
b
100
3
b
17
1
c
80
4
c
90
2
d
30
3
d
30
4
d
50
So I want to identify which are the mandatory id's that the table 'Table02' does not have, and in turn identify which is the 'customer' of each id's that the table 'Table02' does not have.
The resulting table should look like this:
customer
id
b
4
c
2
c
3
d
1
What I have tried so far is a 'rigth join'.
proc sql;
create table table03 as
select
b.id
from table02 a
right join table01 b
on a.id=b.id
where a.id is null;
run;
But that query is not identifying all the id's that should be mandatory.
I hope someone can help me, thank you very much.
here is one way:
select cl.customerid , a.id
from
Table1 a
cross join
( select customerid
from table2
group by customerid
) cl
where not exists ( select 1 from table2 b
where b.customerid = cl.customerid
and b.id = a.id
)
You can use an EXCEPT between two sub-selects. The first creates a matrix of all possibilities, and the except table is a selection of the extant customers.
Example:
data ids;
do id = 1 to 4; output; end;
run;
data have;
input id customer $ weight;
datalines;
1 a 100
2 a 300
3 a 200
4 a 45
1 b 20
2 b 100
3 b 17
1 c 80
4 c 90
2 d 30
3 d 30
4 d 50
run;
proc sql;
create table want(label='Customers missing some ids') as
select matrix.*
from
(select distinct have.customer, ids.id from have, ids) as matrix
except
(select customer, id from have)
;
quit;
If you are doing it in SQL server. Something like #eshirvana above posted, but also you can use with cte:
;with cte as
(
SELECT t1.id, t2.Customer
FROM Table01 t1
cross join (select distinct customer from Table02)
)
SELECT a.customer, a.id FROM cte a
LEFT JOIN Table02 b
ON a.id=b.id AND a.customer=b.customer
where b.id is null

Left join with additional join condition on Raima

I am struggeling with a left join on a Raima database. I'd like to add an additional join condition, but in this case the join behaves like an inner join, thus I am losing some of the expected results.
Example:
TABLE_A
ID
-------
1
2
3
4
.
TABLE_B
A_ID | B
--------
1 | 1
2 | 1
2 | 2
3 | 2
Query
select * from TABLE_A left join TABLE_B
on TABLE_A.ID = TABLE_B.A_ID
and TABLE_B.B = 1
I am expecting the following result:
1 1 1
2 2 1
3 null null
4 null null
E.g. on an Oracle 11g I get the expected result, but on the Raima it shows me only the first two results. What is the problem here and how to fix it?
You need this
select * from A left join
(select * from B where B=1) bd
on A.ID = bd.A_ID
The query you gave will not give you expected result in oracle also. This will.
PS: Please use different names for table and column

SQL Select Statement issue - returning rows conditionally on a 2nd table

I could really use some help with the following SQL Select statement scenario:
I need to select all rows from a table conditionally depending on whether a userID has already entered data into a second table with the same ID.
Example:
Select all rows from TABLE A for idNumber where idNumber not in
TABLE B
but for each idNumber that IS in TABLE B, still return row unless a
specific userID is in that row in TABLE B.
TABLE A
========
idNumber|type|Date
1 A 01/01/01
2 A 01/01/01
3 B 01/01/01
4 B 01/01/01
5 B 01/01/01
TABLE B
========
idNumber|type|userID
1 A 0000
3 B 0000
4 B 1111
userID to exclude records for = 1111
SQL Query should return:
idNumber|type|Date
1 A 01/01/01
2 A 01/01/01
3 B 01/01/01
5 B 01/01/01
Apologies for the long winded post but i hope it makes sense.
Many thanks in advance,
ukjezza.!!
Select idNumber, type, Date
From TableA
Where Not Exists (
Select 1
From TableB
Where TableB.idNumber = TableA.idNumber
And TableB.userID = 1111
)
Another choice:
Select TableA.idNumber, TableA.type, TableA.Date
From TableA
Left Join TableB
On TableB.idNumber = TableA.idNumber
And TableB.userId = 1111
Where TableB.idNumber Is Null
Looks like a LEFT JOIN and COALESCE could take care of it:
SELECT a.*
FROM TableA as a
LEFT JOIN TableB as b
ON a.idNumber = b.idNumber
WHERE COALESCE(b.userID, -1) != 1111
select A.*
from TableA as A
left outer join TableB as B
on A.idNumber = B.idNumber
where B.idNumber is null or
B.userID <> '1111'

SQL query help

Sorry for posting this question again. I rephrased my question a little bit.
I am trying to write a query to return rows from Table-A where multiple rows found in Table-B with STATUS = 1 for each CID column from Table-A.
So in this example CID 100 has two records found in Table-B and STATUS = 1. So I want to write a query to return this row from Table-A. I know this is a weird table design. Please help.
Here are the tables with sample data.
Table-A
-----------------------------------------
AID Name CID
---------------------------------------
10 test1 100
12 test1 100
13 test2 101
14 test2 101
15 test3 102
Table-B
------------------------------------
bID AID status
-----------------------------------
1 10 1
2 12 1
3 14 1
4 15 1
Try this query:
SELECT TableA.CID
FROM TableA
JOIN TableB ON TableA.AID = TableB.AID
WHERE TableB.status = 1
GROUP BY TableA.CID
HAVING COUNT(*) > 1
It returns 100 for your example data.
Something like this?
select aid,
status
from (select aid,
count(*) as cnt
from tableA
group by aid) as aggregated
left join tableB on tableB.aid = aggregated.aid
where aggregated.cnt > 1
If your using SQL:
WITH tableBView AS
(
SELECT AID AS xxxAID
FROM [Table-B]
WHERE status = 1
GROUP BY AID
HAVING COUNT(*) > 0
)
SELECT *
FROM [Table-A]
WHERE EXISTS (SELECT * FROM tableBView WHERE xxxAID = AID)
SELECT *
FROM Table-A a
WHERE a.CID IN
(
SELECT a.CID FROM Table-A a JOIN Table-B b USING (AID)
GROUP BY a.CID
WHERE b.status = 1
HAVING count(*) > 1
)
This is a very verbose way to do it.
Selects all columns from Table-A on rows where AID match between Table-A and Table-B and more than one row with the same CID exists in Table-A:
(Btw, I wouldn't use "-" in your table/column names. Use "_" instead.)
select
derived_table.AID,
derived_table.Name,
derived_table.CID
from
(select
table_A.AID,
table_A.Name,
table_A.CID,
count(table_A.CID) c
from
Table_A
inner join Table_B on (Table_A.AID = table_B.AID)
group by table_A.CID
) derived_table
where
c > 1