Select with double duplicates - mysql

Here is an example
a b
--------
1 10
1 10
2 20
2 20
3 20
3 20
4 NULL
5 NULL
I want this in a mySQL query :
a b
------------
1 10
2 or 3 20
4 NULL
5 NULL
In other words : the set of elements where (there is no duplicates on a and (there is no duplicates on b or b is NULL)).
I try the
SELECT DISTINCT(a), b, but I have 2 rows with b = 20
SELECT a, DISTINCT(b), but I have duplicates on column a and the 2 NULL values are merged.
GROUP BY a or GROUP BY b, equal as the 2 previous queries.
Does anyone have an idea for it ?

SELECT MIN(a) a, b
FROM table1
WHERE b IS NOT NULL
GROUP BY b
UNION
SELECT a, b
FROM table1
WHERE b IS NULL
SQLFiddle Demo
give this a try,
SELECT MIN(a) a, b
FROM table1
GROUP BY COALESCE(b, RAND())
SQLFiddle Demo

I guess this would be faster
SELECT MIN(a) a, b
FROM table1
GROUP by IF( b is null, a, b);
SQLFIDDLE

Related

Insert rows from one table to another but only those rows that have no duplicates

I've seen this, this, this, this and this but my question is different.
I have a Table1:
id c a b rc bid
1 12 4 6 35 4
2 12 4 6 67 7
3 12 4 6 88 8
4 23 4 7 49 3
5 23 5 8 59 8
Table2 also has the same columns but does not have bid column.
A row is considered a duplicate if it has the same values of columns c, a and b. So rows 1, 2 and 3 are considered duplicates because they have 12, 4 and 6.
I want to insert rows of Table1 to Table2, but only those rows that are not duplicates. Which means that rows 1, 2 and 3 won't get inserted to Table2. Only rows 4 and 5 will get inserted because they have no duplicates.
So Table2 will look like this after the inserts:
id c a b rc
1 23 4 7 49
2 23 5 8 59
I know I can get which rows have no duplicates using this query:
select distinct c,a,b,count(*) from Table1 group by c,a,b having count(*) > 1
But am not able to figure out how to insert these to Table2 because the insertion requires specific columns to be specified.
Tried something like this which obviously doesn't work:
insert into Table2 (c, a, b, rc) select distinct c,a,b,count(*) from Table1 group by c,a,b having count(*) > 1
You can use also not in in subselect
INSERT INTO Table2(c, a, b, rc, bid)
SELECT c, a, b, rc, bid
FROM Table1 t1
WHERE (c,a,b) not in ( SELECT c,a,b
FROM Table1 t2
GROUP BY c, a, b
HAVING COUNT(*) > 1
)
You can use NOT EXISTS to exclude duplicate rows:
INSERT INTO Table2(c, a, b, rc, bid)
SELECT
c, a, b, rc, bid
FROM Table1 t1
WHERE NOT EXISTS(
SELECT 1
FROM Table1 t2
WHERE
t2.c = t1.c
AND t2.a = t1.a
AND t2.b = t1.b
HAVING COUNT(*) > 1
)
The HAVING COUNT(*) > 1 will check if there are duplicates.
insert into table2 (c,a,b,rc)
select c,a,b,rc from table1
where id in (select distinct id
from Table1 group by c,a,b having count(*) = 1)
There are many ways to do that. You have already got so many correct answers. Here, I am giving the query based on the way you approached.
INSERT INTO Table2 (c, a, b, rc)
SELECT
c,
a,
b,
rc
FROM
Table1
GROUP BY c, a, b
HAVING count(*) = 1;

deleting all b,a from table mysql

I have a table with 3 fields as below
id a b
1 1 2
2 1 3
3 2 1
4 2 3
5 3 1
6 3 2
(a,b) and (b,a) both exist in this table ( a=1 and b=2 and a=2 and b=1). i need to remove all (b,a) from the above table .
Output:
id a b
1 1 2
2 1 3
4 2 3
i tried a self join like this
select v1.id, v2.id from val v1,val v2 where v1.a=v2.b and v1.b=v2.a
and found out the corresponding ids which match. But , not able to proceed after this. Pls help.
If you want to permanently delete those duplicate records, here's the DELETE statement which uses MySQL's LEAST and GREATEST built-in functions.
DELETE a
FROM tableName a
LEFT JOIN
(
SELECT LEAST(a, b) aa,
GREATEST(a,b) bb,
MIN(ID) min_ID
FROM tableName
GROUP BY aa, bb
) b ON a.ID = b.min_ID
WHERE b.min_ID IS NULL
SQLFiddle Demo
the SELECT statement
SELECT *
FROM tableName
WHERE (LEAST(a, b),GREATEST(a,b), ID)
IN
(
SELECT LEAST(a, b) aa,
GREATEST(a,b) bb,
MIN(ID) min_ID
FROM tableName
GROUP BY aa, bb
)
SQLFiddle Demo
You could do this to select the output you want.
select id, v1.a, v2.a from test v1 left join test v2 on (v1.id = v2.id and v1.a > v2.b)
where v2.id is null
If you want to only show the "half" results:
SELECT *
FROM val
WHERE a <= b ;
and if you want to delete the other half:
DELETE *
FROM val
WHERE a > b ;

MySQL distinct values query

I need help with a relatively simple query. For a table:
A | B | C
----------
2 1 6
2 2 5
3 3 4
4 4 3
5 5 2
6 6 1
I need to have an output like so:
A | B | C
----------
2 1 6
3 3 4
4 4 3
5 5 2
6 6 1
So that each value in A is distinct, but I also get the corresponding values in B and C. I know "select distinct(A) from table" but that only returns the values 2,3,4,5,6 and I need the values in columns B and C, too. Please help. I have a deadline fast approaching. This question is stupid and trivial, but one must walk before they can run. Thanks so much.
Try this:
SELECT T1.A, T1.B, MIN(T1.C) AS C
FROM yourtable T1
JOIN (
SELECT A, MIN(B) AS B
FROM yourtable
GROUP BY A
) T2
ON T1.A = T2.A AND T1.B = T2.B
GROUP BY T1.A, T1.B
SELECT DISTINCT(A), B, C
FROM table
Is there a specific logic behind which distinct A rows you want to select when considering columns B and C?

MySQL sum elements of a column

I have a table with 3 columns (A,B,C). I want to select some rows from the table and then the MySQL to return a single row having the values added on each column.
A B C
1. 2 2 2
2. 4 4 4
3. 6 7 8
MySQL should return in this case, if I select all the three rows:
A B C
1. 12 13 14
select sum(A),sum(B),sum(C) from mytable where id in (1,2,3);
select
sum(a) as atotal,
sum(b) as btotal,
sum(c) as ctotal
from
yourtable t
where
t.id in (1, 2, 3)
Try this:
select sum(a), sum(b), sum(c)
from your_table

mysql two table query problem

a table
a_id a_value
1 text1
2 test2
b table
b_id b_num a_id
1 5 1
2 7 1
3 2 1
4 7 2
5 56 2
Results base a table (edited)
a_id:1 a_value:text1 total:3 records
a_id:2 a_value:text2 total:2 records
How can get this format in sql?
query a table and add a field(total) count b.a_id = a.a_id in table b
thank you..
You can try:
SELECT a.a_id AS id, a.a_value AS value, (SELECT count(b.b_id) AS count FROM b WHERE (b.a_id = a.a_id)) AS total FROM a GROUP BY a.a_id
Then the result for your example using the data from tables a and b:
**id value total**
1 text1 3
2 text2 2
I imagine you have an error in your b table, so I will assume what you call b_id is actually a_id, or your results would be wrong
Anyway you could use:
SELECT COUNT(b.a_id) AS total FROM b GROUP BY (SELECT a.a_id FROM a)
ORDER BY b.a_id
The updated query based on changes to the question
SELECT a_id, a_value, x.total
FROM a
INNER JOIN
(SELECT b.a_id, COUNT(1) AS total
FROM b
GROUP BY (b.a_id)) X
ON a.a_id = x.a_id
ORDER BY a.a_id