2008-09-01 27 views
6

Tôi muốn tìm các cách khác nhau để giải quyết một vấn đề thực tế về cuộc sống mà tôi có: hãy tưởng tượng có một cuộc thi hoặc trò chơi, trong đó người dùng thu thập điểm. Bạn phải tạo truy vấn để hiển thị danh sách người dùng có điểm "n" tốt nhất.Truy vấn SQL để lấy điểm "n" hàng đầu trong danh sách

Tôi đang làm ví dụ để làm rõ. Hãy nói rằng đây là bảng Users, với các điểm thu:

UserId - Points 
1  - 100 
2  - 75 
3  - 50 
4  - 50 
5  - 50 
6  - 25 

Nếu tôi muốn 3 điểm đầu, kết quả sẽ là:

UserId - Points 
1  - 100 
2  - 75 
3  - 50 
4  - 50 
5  - 50 

này có thể được thực hiện trong một cái nhìn hay một thủ tục lưu trữ, như bạn muốn. Db mục tiêu của tôi là Sql Server. Thực ra tôi đã giải quyết vấn đề này, nhưng tôi nghĩ có nhiều cách khác nhau để có được kết quả ... nhanh hơn hoặc hiệu quả hơn tôi.

Trả lời

9

chưa được kiểm tra, nhưng nên làm việc:

select * from users where points in 
(select distinct top 3 points from users order by points desc) 
1

@bosnic, tôi không nghĩ rằng sẽ làm việc theo yêu cầu, tôi không phải là quen thuộc với MS SQL nhưng tôi mong chờ nó trở lại chỉ có 3 hàng và bỏ qua thực tế là 3 người dùng bị ràng buộc ở vị trí thứ 3.

Something như thế này nên làm việc:

select userid, points 
    from scores 
    where points in (select top 3 points 
         from scores 
         order by points desc) 
    order by points desc 
0

@Espo nhờ cho việc kiểm tra thực tế - thêm phụ chọn để sửa chữa cho điều đó.

Tôi nghĩ rằng câu trả lời đơn giản nhất là:

select userid, points from users 
where points in (select distinct top N points from users order by points desc) 

Nếu bạn muốn đặt rằng trong một proc được lưu trữ trong đó có N như một tham số, sau đó bạn sẽ hoặc là phải làm đọc SQL vào một biến sau đó thực hiện nó, hoặc làm các trick đếm hàng:

declare @SQL nvarchar(2000) 
set @SQL = "select userID, points from users " 
set @SQL = @SQL + " where points in (select distinct top " + @N 
set @SQL = @SQL + " points from users order by points desc)" 

execute @SQL 

hoặc

SELECT UserID, Points 
FROM  (SELECT ROW_NUMBER() OVER (ORDER BY points DESC) 
     AS Row, UserID, Points FROM Users) 
     AS usersWithPoints 
WHERE Row between 0 and @N 

Cả hai ví dụ đều cho rằng SQL Server và chưa được thử nghiệm.

0

@ Rob # 37.760:

select top N points from users order by points desc 

Truy vấn này sẽ chỉ chọn 3 hàng nếu N là 3, xem câu hỏi. "Top 3" phải trả về 5 hàng.

1

Làm thế nào về:

select top 3 with ties points 
from scores 
order by points desc 

Không chắc nếu "có quan hệ" hoạt động trên bất cứ điều gì khác SQL Server.

Mở SQL Server 2005 trở lên, bạn có thể vượt qua số "top" như một tham số int:

select top (@n) with ties points 
from scores 
order by points desc 
4

Dưới đây là một trong những hoạt - Tôi không biết nếu nó hiệu quả hơn, và đó là SQL Server 2005+

with scores as (
    select 1 userid, 100 points 
    union select 2, 75 
    union select 3, 50 
    union select 4, 50 
    union select 5, 50 
    union select 6, 25 
), 
results as (
    select userid, points, RANK() over (order by points desc) as ranking 
    from scores 
) 
select userid, points, ranking 
from results 
where ranking <= 3 

Rõ ràng là người đầu tiên "với" là thiết lập các giá trị, vì vậy bạn có thể kiểm tra thứ hai với, và cuối cùng chọn công việc - bạn có thể bắt đầu "với kết quả như ..." nếu bạn đã truy vấn đối với bảng hiện có.

+0

Tôi gặp vấn đề tương tự và cố gắng sử dụng MAX và sau đó tôi đọc trả lời và nhớ DENSE_RANK. Đã cứu tôi rất nhiều thời gian. – DataGirl

0

@ Matt Hamilton

câu trả lời của bạn làm việc với các ví dụ trên nhưng sẽ không hoạt động nếu tập dữ liệu là 100, 75, 75, 50, 50 (nơi mà nó sẽ trở lại chỉ có 3 dòng). TOP VỚI TIES chỉ bao gồm các mối quan hệ của hàng cuối cùng trả lại ...

0

Crucible got it (giả sử SQL 2005 là một tùy chọn).

0

Thực ra một sửa đổi đối với WHERE IN, sử dụng INNER JOIN sẽ nhanh hơn nhiều.

SELECT 
    userid, points 
FROM users u 
INNER JOIN 
(
    SELECT DISTINCT TOP N 
     points 
    FROM users 
    ORDER BY points DESC 
) AS p ON p.points = u.points 
0

Hãy thử điều này

select top N points from users order by points desc 
0

Hey tôi thấy tất cả các câu trả lời khác cắn dài và không hiệu quả câu trả lời của tôi sẽ là:

select * from users order by points desc limit 0,5

này sẽ làm cho top 5 điểm

Các vấn đề liên quan