Please start any new threads on our new site at https://forums.sqlteam.com. We've got lots of great SQL Server experts to answer whatever question you can come up with.

 All Forums
 SQL Server 2005 Forums
 Transact-SQL (2005)
 Unique DepotIds per Account

Author  Topic 

tkizer
Almighty SQL Goddess

38200 Posts

Posted - 2010-08-02 : 17:38:12
Need some help on a T-SQL 2005 query.

Need to produce a query that will show all of the unique DepotIds for each Account. If there is more than one row for an Account+DepotId pair, then need to get the one with the greatest TempID. I need all 5 columns returned in the result set.

Below is DDL, sample data, and expected output.



CREATE TABLE [dbo].[#Temp] (
[TempID] BIGINT IDENTITY(1,1) NOT NULL PRIMARY KEY CLUSTERED,
[Account] INT NOT NULL,
[DepotId] SMALLINT NOT NULL,
[Insert_Time] DATETIME NOT NULL,
[FullName] NVARCHAR(50) NULL)
ON [PRIMARY];

INSERT INTO #Temp VALUES (123, 100, N'2010-07-27 09:50:00', N'Name 1');
INSERT INTO #Temp VALUES (123, 100, N'2010-07-27 10:50:00', N'Name 2');
INSERT INTO #Temp VALUES (123, 200, N'2010-07-27 10:50:00', N'FooBar');

INSERT INTO #Temp VALUES (456, 100, N'2010-07-27 09:50:00', N'Another Name 1');
INSERT INTO #Temp VALUES (456, 100, N'2010-07-27 09:50:00', N'Another Name 2');
INSERT INTO #Temp VALUES (456, 300, N'2010-07-27 11:50:00', N'San Diego');


SELECT * FROM #Temp;

-- This is the result I need the query to produce:

-- 2 123 100 2010-07-27 10:50:00.000 Name 2
-- 3 123 200 2010-07-27 10:50:00.000 FooBar
-- 5 456 100 2010-07-27 09:50:00.000 Another Name 2
-- 6 456 300 2010-07-27 11:50:00.000 San Diego

DROP TABLE #Temp


Please help, thanks!

Tara Kizer
Microsoft MVP for Windows Server System - SQL Server
http://weblogs.sqlteam.com/tarad/

Subscribe to my blog

Bustaz Kool
Master Smack Fu Yak Hacker

1834 Posts

Posted - 2010-08-02 : 18:39:15
[CODE]select
[TempID],
[Account],
[DepotId],
[Insert_Time],
[FullName]
from
(
select
[TempID],
[Account],
[DepotId],
[Insert_Time],
[FullName],
row_number() over (partition by Account, DepotId order by Insert_Time DESC) rn
from #Temp
) a
where a.rn = 1[/CODE]

=======================================
A couple of months in the laboratory can save a couple of hours in the library. -Frank H. Westheimer, chemistry professor (1912-2007)
Go to Top of Page

tkizer
Almighty SQL Goddess

38200 Posts

Posted - 2010-08-02 : 18:42:09
That one is close, but it gives me 4 instead of 5 for the 456,100 pair. Is there an easy way to get 5 back instead?

In other words, yours is returning 2,3,4,6 for TempID. But I need 2,3,5,6 according to the developer's requirements.

Tara Kizer
Microsoft MVP for Windows Server System - SQL Server
http://weblogs.sqlteam.com/tarad/

Subscribe to my blog
Go to Top of Page

malpashaa
Constraint Violating Yak Guru

264 Posts

Posted - 2010-08-02 : 18:42:33
Try this:

SELECT TempID, Account, DepotId, Insert_Time, FullName
FROM (SELECT TempID, Account, DepotId, Insert_Time, FullName,
ROW_NUMBER() OVER(PARTITION BY Account, DepotId ORDER BY TempID DESC) AS row_num
FROM #Temp) as t
WHERE row_num = 1;


Note: I have not test it thoroughly.
Go to Top of Page

tkizer
Almighty SQL Goddess

38200 Posts

Posted - 2010-08-02 : 18:45:36
Bingo! ORDER BY TempID is what I need. Thanks!

Thanks Bustaz Kool too!



Tara Kizer
Microsoft MVP for Windows Server System - SQL Server
http://weblogs.sqlteam.com/tarad/

Subscribe to my blog
Go to Top of Page

Bustaz Kool
Master Smack Fu Yak Hacker

1834 Posts

Posted - 2010-08-02 : 18:50:10
At long last WE get to help YOU! Woo and Hoo!

=======================================
A couple of months in the laboratory can save a couple of hours in the library. -Frank H. Westheimer, chemistry professor (1912-2007)
Go to Top of Page

tkizer
Almighty SQL Goddess

38200 Posts

Posted - 2010-08-02 : 18:52:56
quote:
Originally posted by Bustaz Kool

At long last WE get to help YOU! Woo and Hoo!






I'm not such a great SQL developer, but I'm a damn good DBA.

A good DBA doesn't need to be a good SQL developer; a good DBA just needs to know about SQLTeam.com.

Tara Kizer
Microsoft MVP for Windows Server System - SQL Server
http://weblogs.sqlteam.com/tarad/

Subscribe to my blog
Go to Top of Page

slimt_slimt
Aged Yak Warrior

746 Posts

Posted - 2010-08-02 : 18:54:54
try this:


select
t.*
from
(
select
max_tempID
from
(
select account
,depotID
,count(*) as nof
,max(tempID) as max_tempID
from #temp
group by account, depotID
having count(*) > 1
) as x
union all
select
max_tempID
from
(
select account
,depotID
,count(*) as nof
,max(tempID) as max_tempID
from #temp

group by account, depotID
having count(*) = 1
) as x
) as y
join #temp as t
on t.tempID = y.max_tempId

and / or

select
*
from
(select *,row_number() over (partition by account, depotID order by tempID desc) as r_n from #temp
) as x
from #temp
where r_n = 1
Go to Top of Page

tkizer
Almighty SQL Goddess

38200 Posts

Posted - 2010-08-02 : 18:56:23
Thanks slimt. That solution would be how to do it in 2000 or lower, but ROW_NUMBER() function is more efficient for 2005 and greater.

Tara Kizer
Microsoft MVP for Windows Server System - SQL Server
http://weblogs.sqlteam.com/tarad/

Subscribe to my blog
Go to Top of Page

slimt_slimt
Aged Yak Warrior

746 Posts

Posted - 2010-08-02 : 19:02:49
everyone is so fast, while i'm having trouble writing in small reply windonw :S
and malpashaa has same solution. he he he

I tend to write sql2000 and sql2005+ solutions. one must not get to confy with sql2005+ coding :P
Go to Top of Page
   

- Advertisement -