Lets say I have a table containing several hundred million rows that looks something like this:
memID | foo | bar | foobar
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
.
.
.
10001 | blah | blah | blah
10001 | blah | blah | blah
I need a query that will return the top N rows for each memID in a range of member IDs. For example, if N = 3 and the range is 0-2 it should return
memID | foo | bar | foobar
1 | blah | blah | blah
1 | blah | blah | blah
1 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
2 | blah | blah | blah
I've considered a couple approaches, first creating a massive
SELECT TOP (3) *
FROM table
WHERE memID = 0
UNION ALL
SELECT TOP (3) *
FROM table
WHERE memID = 1
.
.
.
query in code. This isn't really a realistic option for probably obvious reasons.
The second approach is to create a temporary table and loop over the range of memIDs inserting the TOP 3 for each memID into that temporary table.
WHILE @MemID < 10000 AND @MemID > 0
BEGIN
INSERT INTO tmp_Table
SELECT TOP (3) *
FROM table
WHERE memID = @MemID
SET @MemID = @MemID + 1
END
This works, but I'm wondering if there is a more elegant single query solution that I'm missing.
Cadaeic gave me an answer that works without tinkering, but thank you to everyone that suggested analytics, it looks like I have some serious reading to do.