前幾天在一個群裡面,有位網友問:在一個Book表裡面裡有字段AuthorID與Author表關聯,現在要求按PublishDate字段倒序排列,列出每個作者的前五本書。要求有沒有一條語句搞定的. 當時有個網友說不能一條語句解決問題,說只能用游標或臨時表來解決。恰好我前陣子在整報表時遇到過類似的問題,當時解決過這個問題。當時我就告訴他用ROW_NUMBER與PARTITION來解決(前提是SQL SERVER 05或以上版本)。恰好現在有時間。正好把這個整理一下,即是對知識的梳理、鞏固、總結,也希望能給其他人一些幫助
建表腳本
IF OBJECT_ID(N'Author') IS NOT NULL BEGIN DROP TABLE dbo.Author; END ELSE BEGIN CREATE TABLE dbo.Author ( AuthorID INT IDENTITY(1,1) PRIMARY KEY, AuthorName NVARCHAR(50), NickName NVARCHAR(50), Place NVARCHAR(120), BirthDay SMALLDATETIME ) END GO IF OBJECT_ID(N'Book') IS NOT NULL BEGIN DROP TABLE dbo.Book ; END ELSE BEGIN CREATE TABLE dbo.Book ( ID INT IDENTITY(1, 1) , BookName NVARCHAR(35) , --書名 PublishDate DATETIME , --出版時間 Publisher NVARCHAR(50) , --出版商 BookType INT , --書籍類型 AuthorID INT FOREIGN KEY REFERENCES dbo.Author(AuthorID) ) END GO
--生成實驗數據 INSERT INTO dbo.Author VALUES('張三', '三峰', '北京', '1973-12-28') INSERT INTO dbo.Author VALUES ('王五', '絕望的中春天', '湖南', '1978-5-23' ) INSERT INTO dbo.Author VALUES ('趙四', '趙四', '上海', '1978-5-23' ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書1' , '1988-12-24' , '北京圖書出版社' , 1 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書2' , '1983-12-04' , '長城圖書出版社' , 2 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書3' , '1995-12-19' , '教育圖書出版社' , 2 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書4' , '1996-12-04' , '教育圖書出版社' , 2 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書5' , '2004-04-26' , '教育圖書出版社' , 2 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '張三書6' , '2009-12-15' , '教育圖書出版社' , 2 , 1 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '王五1' , '2003-06-15' , '教育圖書出版社' , 2 , 2 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '王五2' , '2007-09-25' , '上海圖書出版社' , 1 , 2 ) INSERT INTO dbo.Book ( BookName , PublishDate , Publisher , BookType , AuthorID ) VALUES ( '趙四1' , '2010-09-25' , '上海圖書出版社' , 1 , 3 )
下面就是解決問題的腳本
SELECT * FROM ( SELECT ROW_NUMBER() OVER (PARTITION BY A.AuthorID ORDER BY B.PublishDate DESC) AS RowNum, A.AuthorName, B.BookName, B.PublishDate FROM dbo.Book B INNER JOIN dbo.Author A ON A.AuthorID = B.AuthorID ) T WHERE T.RowNum <= 5
作者:潇湘隱者
出處:http://www.cnblogs.com/kerrycode/