I can't find the answer to the current question with my versions of SQL so hopefully someone can help me out.
I am using MySQL with SQLPro as the client or I can use PostgreSQL pgAdmin 4.
scenario I am trying to update a null value with the previous not null value.
here is my table:
primary_id name address id
1 bob 123 main 100
2 jane 123 main NULL
3 mike 217 2nd 200
4 jeff 217 2nd NULL
How can I populate the null values with the not null values so that the address/ID grouping remain constant down my columns?
thanks!!!
If you want to update the table, this will work in Postgres:
update t
set id = (select t2.id
from t t2
where t2.address = t.address and t2.id is not null
fetch first 1 row only
)
where id is null;
In MySQL, this will work:
update t join
(select address, max(id) as max_id
from t
group by address
) tt
on t.address = tt.address
set t.id = tt.max_id
where t.id is null;
You can try updating the table with itself. I inserted your table into a users table I created in postgres:
UPDATE users
SET
id = _users.id
FROM
(
SELECT DISTINCT
address,
id
FROM users
WHERE id IS NOT NULL
GROUP BY
address,
id
) _users
WHERE
_users.address = users.address
AND users.id IS NULL;
So the idea is that I grab all all the non-null address and id groups (assuming address is always paired with the same id. I call this _users.
Match _users.address with your original users.address. Make sure that you are only updating the NULL users.id.
Related
I have a one query for select ids from table and another query for update the table values. These are the queries used.
for select ids
select id from table_1 where orderId = 41 AND status = 1
for update
UPDATE table_1 SET orderId = '17' WHERE id IN (1,2,3,4,5,6,.....,n);
This two queries working properly. But when try to this code its not working. I want to update orderId update 41 to 17 in all the records selected
UPDATE table_1 SET orderId = '17' WHERE id IN (select id from table_1 where orderId = 41 AND status = 1 );
This query is returns error. Any suggestion to correct this error.
Thank You
The problem is that MySQL does not allow you to use the same table in subqueries in an update or delete. I think you can simplify the logic, so the subquery is not needed.
Why not just use this?
UPDATE table_1
SET order_id = '17'
WHERE order_id = 41 AND status = 1;
Note: If order_id is a number, use 17 not '17' -- don't mix data types.
This assumes that id is unique.
Alternatively, if you really need list of ids, you can also use a JOIN:
UPDATE table_1 t1 JOIN
(SELECT tt1.*
FROM table_1 tt1
WHERE tt1.order_id = 41 AND tt1.status = 1
) tt1
ON tt1.id = t1.id
SET t1.order_id = 17;
I need an update statement to resolve some issues with duplicates in a table on MySQL. The table structure is shown below. I need a MySQL statement that will set the value of duplicate as NULL except the first one, i.e the one with the lowest id. Here the id is the primary key.
This is an example of what I have:
id name
1 foo
2 foo
3 bar
4 NULL
5 NULL
6 foo
7 bar
This is the desired result:
id name
1 foo
2 NULL
3 bar
4 NULL
5 NULL
6 NULL
7 NULL
The table has other columns with useful information. Hence, the row can't just simply be deleted.
I would write this as:
UPDATE t JOIN
(SELECT name, MIN(id) as min_id
FROM t
GROUP BY name
) tt
ON t.name = tt.name and t.id > tt.min_id
SET t.name = NULL;
I think the logic is easier to follow using JOIN. Basically, it says to find the minimum id for each name. Then set all other rows for the same name to NULL.
Your UPDATE query can include a JOIN.
e.g. join the minimum id for each name and only update where the id is not the minimum.
UPDATE
t
LEFT OUTER JOIN (
SELECT
MIN(id) AS id
FROM
t
GROUP BY
name
) t1 ON t.id = t1.id
SET
t.name = NULL
WHERE
t1.id IS NULL
DB Fiddle
UPDATE t JOIN
(SELECT name, MIN(id) as min_id
FROM t
WHERE name IS NOT NULL
GROUP BY name
HAVING COUNT(*) > 1
) tt
ON t.name = tt.name and t.id > tt.min_id
SET t.name = NULL;
example table:
id | value
----------
1 | abc
1 | cb3
1 | dsf
2 | sss
2 | d3
So if the input is "cb3" I want to get all rows with id 1, if the input is "sss" I want to get all rows with id 2. Can this be done with one query instead of two ? (first query is find id and second query bring rows for found id). Also, would a one query approach be faster ?
Thank you in advance.
you could try this :
SELECT *
FROM TABLE my_table
WHERE id IN (SELECT id
FROM TABLE my_table
WHERE value = input
)
Try the following, where you replace 'sss' with the value you are searching for:
select * from table t1
where t1.id in (select id from table t2 where value = 'sss')
Note that value seems not to be a key, such that you might get two different groups of ids in your result. That's also the reason why I proposed an t1.id IN (select id ... rather than an t1.id = (select id ....
You can solve it using inner join also.
SELECT S.*
FROM dataset AS S
INNER JOIN dataset AS T
ON S.id = T.id
WHERE T.value = 'cb3';
I'm trying to find a query to resolve my issue:
i have something like this on my database:
i need a query that selects all users that have role 5 but if for some reason they have any other role it should skip them
SELECT user_id FROM user_table WHERE roleid = 5 AND (roleid != 3 OR roleid != 1)
That still returns user 64
I think you are looking for a not exists clause:
select *
from t
where roleid = 5 and
not exists (select 1
from t t2
where t2.user_id = t.user_id and t2.roleid <> 5
);
Alternatively, if you are just looking for such users, then you can use group by and having:
select user_id
from t
group by user_id
having min(roleid) = max(roleid) and min(roleid) = 5;
(If roleid could be NULL, the logic would need to take this into account.)
I have a database table with the columns: email, name, id
There are duplicate records with the same email and name (ids may or may not be different)
I want to remove all duplicates and not keep any of them.
Example
email | name | id
-------------------------------------------------
a#b.com | a | 2 --- remove
a#b.com | a | 4 --- remove
b#c.com | b | 3
c#d.com | c | 5
What sql query can I use in phpmyadmin to do this?
You could use EXISTS:
DELETE FROM TableName t1
WHERE EXISTS
(
SELECT 1 FROM TableName t2
WHERE t1.id <> t2.id
AND COALESCE(t1.email,'') = COALESCE(t2.email,'')
AND COALESCE(t1.name,'') = COALESCE(t2.name,'')
)
I've used COALESCE to also delete duplicates if the emails or names are null.
In MySQL, you should do this with a join:
delete t
from example t join
(select email, name
from example
group by email, name
having count(*) > 1
) todelete
on t.email = todelete.email and t.name = todelete.name;
Unfortunately, MySQL does not support simple subqueries on the table being modified in an update or delete statement.
EDIT:
Deleting a lot of records can be a performance bottleneck. To get around this, create a temporary table with the records you want, truncate the original table, and re-insert them.
So, try this:
create temporary table tempt as
select t.*
from example t join
(select email, name
from example
group by email, name
having count(*) = 1
) tokeep
on t.email = tokeep.email and t.name = tokeep.name;
truncate table example;
insert into example
select * from tempt;
Try the select query first to be sure it has reasonable performance and does what you want.
DELETE n1 FROM tablename n1, tablename n2 WHERE n1.email = n2.email