I have a table #tempTest with data like this:
ID Name
1 A
2 AB
3 ABC
4 ABCD
5 ABCDE
6 ABCDEF
7 X
8 QRWXYZ
Now I need the shortest name from the table.
I've tried this way:
SELECT TOP 1(name) Smallest FROM #tempTest
GROUP BY name
ORDER BY LEN(name)
And that represents:
Smallest
A
But what I need is:
ID Name
1 A
7 X
SELECT TOP 1 WITH TIES (name) Smallest FROM #tempTest
GROUP BY name
ORDER BY LEN(name)
SELECT id, name FROM #tempTest
WHERE LEN(name) = (SELECT MIN(LEN(name)) FROM #tempTest)
Related
I want to update one table using another table on field "Id" such that it wont create duplicates
let say my first table is Table1 and second table is Table2 . I would like to update the row in Table1 from Table2 when the Id is matching
I am aware of using UNION function but this applies to entire columns where I only need to consider a single column. https://docs.snowflake.com/en/sql-reference/operators-query.html#union-all
Example of my Tables
Table1
Id name number value
1 a 8 100
2 b 8 100
3 c 8 100
4 d 8 100
Table2
Id name number value
3 c 8 99
4 d 6 100
5 e 7 100
Expected output
Id name number value
1 a 8 100
2 b 8 100
3 c 8 99
4 d 6 100
5 e 7 100
Please note that in the output table row with Id 3,4 has be updated and new Id 5 is inserted.
PS: It would be better if someone could provide me the select statement to get the output table.
The constuct you are searching for is called MERGE:
CREATE OR REPLACE TABLE trg(Id INT, name VARCHAR, number INT, value INT)
AS SELECT 1 ,'a', 8, 100
UNION SELECT 2 ,'b', 8, 100
UNION SELECT 3 ,'c', 8, 100
UNION SELECT 4 ,'d', 8, 100;
CREATE OR REPLACE TABLE src(Id INT, name VARCHAR, number INT, value INT)
AS SELECT 3 ,'c', 8, 99
UNION SELECT 4 ,'d', 6, 100
UNION SELECT 5 ,'e', 7, 100;
Query:
MERGE INTO trg
USING src
ON trg.Id = src.Id
WHEN MATCHED THEN UPDATE SET name = src.name,
number = src.number,
value = src.value
WHEN NOT MATCHED THEN INSERT (ID, name, number, value)
VALUES (src.Id, src.name, src.number, src.value);
SELECT * FROM trg;
Output:
EDIT:
PS: It would be better if someone could provide me the select statement to get the output table.
UNION ALL combined with QUALIFY could be used:
WITH cte AS (
SELECT *, 1 AS priority FROM trg
UNION ALL
SELECT *, 0 AS priority FROM src
)
SELECT Id, Name, Number, Value
FROM cte
QUALIFY ROW_NUMBER() OVER(PARTITION BY ID ORDER BY Priority) = 1
ORDER BY Id;
How to select the value from the table based on category_id?
I have a table like this. Please help me.
Table A
ID Name category_id
-------------------
1 A 1
2 A 1
3 B 1
4 C 2
5 C 2
6 D 2
7 E 3
8 E 3
9 F 3
How to get the below mentioned output from table A?
ID Name category_id
--------------------
1 A 1
2 A 1
4 C 2
5 C 2
7 E 3
8 E 3
Give a row number for each row based on group by category_id and sort by ascending order of ID. Then select the rows having row number 1 and 2.
Query
;with cte as (
select [rn] = row_number() over(
partition by [category_id]
order by [ID]
), *
from [your_table_name]
)
select [ID], [Name], [category_id]
from cte
where [rn] < 3;
Kindly run this query It really help You Out.
SELECT tbl.id,tbl.name, tbl.category_id FROM TableA as tbl WHERE
tbl.name IN(SELECT tbl2.name FROM TableA tbl2 GROUP BY tbl2.name HAVING Count(tbl2.name)> 1)
Code select all category_id from TableA which has Name entries more then one. If there is single entry of any name group by category_id then such data will be excluded. In above example questioner want to eliminate those records that have single Name entity like wise category_id 1 has name entries A and B among which A has two entries and B has single entry so he want to eliminate B from result set.
I want to Update only top 1 OR only 1 row of a column where a column values are same.
(Just logical explanation don't go on syntax)
LIKE:
Update [Total] = (value from a another table with a common column)
but need to update only top 1 row OR any one row to the current (updating) table not all rows matching column value...
e.g
Table 1:
Skill Value
abc 3
def 4
xyz 3.5
Table 2:
Name Skill MyValue MyValue2(ColumnNeedsToBeUpdated)
Ram abc 3
shyam abc 4
Mohan abc 5
Raju xyz 4
Ratan xyz 6
Now I want to Update MyValue2 based on Table1 column Skill Value = MyValue2 but I want to update anyone OR top 1 row in Table2 NOT ALL Please help
Expected Output:
Name Skill MyValue MyValue2(ColumnNeedsToBeUpdated)
Ram abc 3 3
shyam abc 4
Mohan abc 5
Raju xyz 4 3.5
Ratan xyz 6
OR Alternate output can be:
Name Skill MyValue MyValue2(ColumnNeedsToBeUpdated)
Ram abc 3 Value from Table1 / no. of records with skill abc (3/3)
shyam abc 4
Mohan abc 5
Raju xyz 4 Value from Table1 / no. of records with skill xyz (3.5/2)
Ratan xyz 6
In Table 2, give a row number based on group by Skill column and order by MyValue column. And then updated the rows which having row number1 with Value from Table 1.
Query
;with cte as(
select [rn] = row_number() over(
partition by Skill
order by [MyValue]
), *
from [Table2]
)
update t1
set t1.[MyValue2] = t2.[Value]
from cte t1
join [Table1] t2
on t1.[Skill] = t2.[Skill]
where t1.[rn] = 1;
Currently I'm working on a stored procedure to update the sort order of a table. The idea is to make sure that the correct rows are swapped.
INPUT: ToMoveID INT, Up BIT (1 up, 0 down)
SERVER: MSSQL 2012
example to use:
ID SortOrder UseForSwap
1 1 Yes
2 NULL No
3 2 Yes
4 NULL No
5 3 Yes
The idea is to put the row with ID 5 higher, the ID of 3 is unkown at this point. How Can i get the ID of the row with te first sortorder higher as the current?
Sample values: TomoveID = 5, Up = 1
After sorting the result shoud be:
ID SortOrder UseForSwap
1 1 Yes
2 NULL No
3 3 Yes
4 NULL No
5 2 Yes
Thanks in advance
You can search for a row with the biggest SortOrder that is less than SortOrder of ID 5 row in this way:
SELECT TOP 1
tbl.ID
FROM YourTable tbl
WHERE tbl.SortOrder < (SELECT SortOrder FROM YourTable tbl2 WHERE tbl2.ID = 5)
ORDER BY
tbl.SortOrder DESC
i have a table named customer_age that loks like this:
ID 1 2 3 4 5 6 7 8 9
NAME JIM JIM JIM NICK NICK NICK Paul Paul Paul
VALUE 20 13 12 10 20 8 4 24 14
and i want to display only the first record from each name. Something like this
ID 1 4 7
NAME JIM NICK Paul
VALUE 20 10 4
So far i have not been able to work it out.
i use sql server 2005
Any help would be appreciated...
Try using a subselect to find the lowest ID for each name, and use that set of IDs to pull the records from the main table:
SELECT ID, Name, Value
FROM customer_age
WHERE ID IN
(
SELECT MIN(ID) AS ID
FROM customer_age
GROUP BY Name
)
Just select the first record for each name using cross apply:
SELECT
ca.ID, ca.NAME, ca.VALUE
FROM customer_age c
CROSS APPLY (SELECT TOP 1 ID, NAME, VALUE
FROM customer_age ca
WHERE ca.NAME = c.NAME ORDER BY ID) ca
ORDER BY ca.ID
How about using window functions??
SELECT Id, Name, Value
FROM (
SELECT Id, Name, Value, ROW_NUMBER() OVER (PARTITION BY Name ORDER BY Id ASC) AS rowNum
FROM customer_age
) AS sub
WHERE rowNum = 1
Assuming first record means highest ID, you may try your query with descending orderby ID and TOP n.