i trying to update a column in my table for several rows at the same time.
i want get the value to update from an another table which has a foreignkey.
Table Table1:
Id Primary
UserNumber INT
Table Table2
Id Primary
Id_T1 ForeignKey
UserId INT
OrderNumber INT
can someone help with this pls?
Note: In the Table T2 i need the UserId Value Where the ordernumber has the maximum value.
for example:
Id_T1 UserId OrderNumber
15 24 1
15 55 2
15 72 3
the value i want to receive is the 72.
i have try this:
update T1 set T1.UserNumber = T2.UserId
FROM Table1 AS T1
INNER JOIN Table2 AS T2
ON T1.Id = T2.IdMain
WHERE T1.Id = T2.IdMain
AND T2.OrderNumber = (SELECT MAX(T2.OrderNumber) FROM Table2)
but i get this error:
Msg 147, Level 15, State 1, Line 6 An aggregate may not appear in the
WHERE clause unless it is in a subquery contained in a HAVING clause
or a select list, and the column being aggregated is an outer
reference.
You don't need to use alias name in inner query.
Try this:
UPDATE T1
SET T1.UserNumber = T2.UserId
FROM Table1 AS T1 INNER JOIN
Table2 AS T2 ON T1.Id = T2.IdMain
WHERE T1.Id = T2.IdMain
AND T2.OrderNumber = (SELECT MAX(OrderNumber) FROM Table2)
Related
I have a pretty simple case with two tables:
create table Table1
(
Id int,
Name varchar(255),
)
and
create table Table2
(
Id int,
Name varchar(255),
ParentId int
)
I want to get some count of rows (for example offset 10 and fetch 5) by Table1 with joining of Table2. Between Table1 and Table2 I have a relation one-to-many.
I try to write something like that:
SELECT *
FROM Table1
JOIN Table2 AS t2 ON Table1.Id = t2.ParentId
ORDER BY Table1.Id
OFFSET 10 ROWS FETCH NEXT 5 ROWS ONLY
As a result I get 5 rows from joined tables. But I want to get 5 rows from Table1 and then join to them Table2. Have someone any ideas how to do that?
SELECT *
FROM (SELECT *
FROM Table1
ORDER BY Id
OFFSET 10 ROWS FETCH NEXT 5 ROWS ONLY) AS t1
JOIN Table2 AS t2 ON t1.Id = t2.ParentId
Thank you all! That was easy)
I have two tables: table1 and table2:
table1 has columns id and integer
table2 has columns id and boolean
table2 can have multiple rows with the same id
I want to update the integer column of table1 by looking at all rows with the same id in table2 and seeing if any of the boolean values are true. If so I want table1.integer to be 1, else I want it to be 0.
I have tried something like this:
UPDATE table1,
(
SELECT table2.id, Sum(table2.boolean) > 0
) AS 'condition'
from table2
WHERE 1
GROUP BY table2.id) table3
SET table1.integer =IF(table3.condition, 1, 0) where table1.id = table3.id
And it seems to work, but I wanted to ask if there is a nicer/cleaner/more succinct way of updating the rows of table1 according to multiple rows of table2.
I would recommend EXISTS:
UPDATE table1 t1
SET t1.integer = (EXISTS (SELECT 1
FROM table2 t2
WHERE t2.id = t.id AND
t2.boolean
)
);
This can take advantage of an index on table2(id, boolean). With such an index, it should be faster than an approach that uses JOIN and AGGREGATION.
The syntax of your query is MySql like, so you can do a join like this:
UPDATE table1 t1 INNER JOIN (
SELECT id, MAX(boolean) maxboolean
FROM table2
GROUP BY id
) t2 ON t2.id = t1.id
SET t1.integer = t2.maxboolean
If there are ids in table1 without a corresponding id in table2 and you want the integer column for them to be updated to 0 then use a LEFT join:
UPDATE table1 t1 LEFT JOIN (
SELECT id, MAX(boolean) maxboolean
FROM table2
GROUP BY id
) t2 ON t2.id = t1.id
SET t1.integer = COALESCE(t2.maxboolean, 0)
I have two tables.
Table1 structure NOT NULL.
Table2 some value NULL.
I want update table2 to table1 ,
I want when select value if null don't update and skip next column have value to update.
My Table
table1 value(table1) table2 value(table2)
t1ID 1234 t2ID 1234
t1Name Bear t2Name null
t1Adress 87/25 t2Adress 99/77
t1Tel 01254798535 t2Tel null
My Code
UPDATE table1
SET t1Name = (SELECT t2Name
FROM table2
WHERE t2Name IS NOT NULL
),
t1Adress = (SELECT t2Adress
FROM table2
WHERE t2Adress IS NOT NULL
),
t1Tel = (SELECT t2Tel
FROM table2
WHERE t2Tel IS NOT NULL
)
FROM table1,table2
WHERE t1ID = '1234' AND t2ID ='1234'
When I execute I get error:
SQL error : Msg 512, Level 16, State 1, Line 1 Subquery returned more
than 1 value. This is not permitted when the subquery follows =, !=,
<, <= , >, >= or when the subquery is used as an expression. The
statement has been terminated.
How can I fix it?
I think you intend:
UPDATE t1
SET t1Name = COALESCE(t2.t2Name, t1.t1Name),
t1Adress = COALESCE(t2.t2Adress, t1.t1Adress),
t1Tel = COALESCE(t2.t2Tel, t1.t2Tel)
FROM table1 t1 JOIN
table2 t2
ON t1.t1id = t2.t2id
WHERE t1.t1ID = 1234;
Note that I removed the single quotes on '1234'. Ids are usually numbers so they should be compared to numbers.
Your code fails because you are using subqueries instead of the values from the join. You seem to have multiple rows in table2, so you are getting the subquery returned more than one row error.
The following query replaces the null values with table1 values and updates the rest from table2 values
UPDATE T1 SET T1.t1Name = IsNull(T2.t2Name,T1.t1Name),
T1.t1Adress = IsNull(T2.t2Adress,T1.t1Adress),
T1.t1Tel = IsNull(T2.t2Tel,T1.t1Tel)
FROM table1 TI
INNER JOIN table2 T2 ON T1.t1ID = T2.t2ID
Try the following select query to check your result
SELECT T1.t1Name,IsNull(T2.t2Name,T1.t1Name),T1.t1Adress,IsNull(T2.t2Adress,T1.t1Adress),T1.t1Tel,IsNull(T2.t2Tel,T1.t1Tel)
FROM table1 TI
INNER JOIN table2 T2 ON T1.t1ID = T2.t2ID
I have read that SELECT ... WHERE SELECT ... is slow, and that I should use joins instead.
But I don't know how to replace this code
SELECT Id
FROM Table1
Where
(
Data1 IS NULL
OR
(
Data2=1
AND
(SELECT 1 FROM Table2 WHERE Table2.Id=Table1.Id) IS NULL
)
)
AND
(SELECT 1 FROM Table3 WHERE Table3.Id=Table1.Id) IS NULL
with joins.
The tables have the following structure:
Table1:
Id: INTEGER PRIMARY KEY
Data1: XML
Data2: INTEGER
Table2:
Id: INTEGER
Table3:
Id: INTEGER PRIMARY KEY
select Id from Table1 where
Id not in (select Id from Table3) and
(Data1 is null or
(Data2 = 1 and Id not in (select Id from Table2)));
or, if you really want joins:
select Id from Table1 left join Table2 on (Table1.Id = Table2.Id)
left join Table3 on (Table1.Id = Table3.Id)
where Table3.Id is null and
(Data1 is null or
(Data2 = 1 and Table2.Id is null));
I don't expect much difference in performance between these two. The query would likely benefit from an index on Table2.Id (you have one on Table3.Id by virtue of it being a primary key).
There are two key parts to moving subqueries from in to the from clause. The first is to use left outer join, so no rows from the first table inadvertently drop out. The second is to use select distinct for each subquery, to avoid unwanted duplicates.
Applied to your query, the result is:
SELECT t1.Id
FROM Table1 t1 left outer join
(select distinct id
from Table2
) t2
on t1.id = t2.id left outer join
(select distinct id
from Table3
) t3
on t1.id = t3.id
Where(t1.Data1 IS NULL OR
(t1.Data2=1 and t2.id is null)
) and
t3.id is null;
There are two table TABLE1 and TABLE2 in which there is a common field ID. I wanted to retrieve values from TABLE2 that doesnot match in TABLE1 based on ID value.
select * from TABLE2 where subject = 1 and ID NOT IN (select ID from TABLE1 where subject = 1)
Sample:
TABLE1 ID SUBJECT 1 1
TABLE2 ID SUBJECT 1 1 2 1
The expected result is 2 and it works fine.
But when TABLE1 is empty or the inner select ID from TABLE1 where subject = 1 returns empty, the whole select statement returns empty.
But the expected result is 1, 2
Is there any way to achieve this ?
Use a left join
select t2.*
from table2 t2
left outer join table1 t1 on t1.id = t2.id and t1.subject = 1
where t2.subject = 1
and t1.id is null
See a good explanation of joins
I think you can use not exists also for this work -
select * from TABLE2 where subject = 1 and NOT exists
(select 1 from TABLE1 where subject = 1 and table1.id = table2.id)