隨著sql server版本的公升級,常用的方法有三種:top,row_number,offset/fetch next。
一. top
(1) 利用order by正反排序
declare @page_no intdeclare @page_size
intselect *
from (select top @page_size *
from (select top @page_size*@page_no * from
split_pages order by id) a
order by id desc) b
order by id
做完最裡層select後,再對派生表查詢時,index就沒有效果了,而且越往後面要top更多的資料,這種寫法會更慢。
(2) 利用not in或者not exists
declare @page_no intdeclare @page_size
intselect top @page_size *
from
split_pages
where id not in (select top @page_size*(@page_no-1) id from
split_pages order by id)
order by id
通常在寫sql語句時,用in/exists不一樣,如果邏輯不變的話, exists的效率高。
不過,利用not in分頁,和用not exists效果基本一樣,因為都需要掃完全部資料。
(3) 利用id大於max(id)
declare @page_no intdeclare @page_size
intselect top @page_size *
from
split_pages
where id > (select max(id) from (select top @page_size*(@page_no-1) id from
split_pages order by id) t)
order by id
在使用top分頁時,這種用法效率最高。
二. row_number
sql server 2005開始的新語法,和oracle,db2中的row_number()類似。效能比用top有所提公升。
在利用row_number分頁時,總頁數/行數的計算,可以有這幾種寫法。
(1) 單獨的sql語句去獲得總行數
select count(*) as totrowsfrom
split_pages
godeclare @page_no
intdeclare @page_size
intset @page_no = 2
set @page_size = 10
;with tmpas(
select *,
row_number() over(order by id) num
from
split_pages
)select
id, name
from
tmpwhere num between (@page_size*(@page_no-1)+1) and @page_size*@page_no
order by num
分頁開始與結束:
a.起始頁從1開始
int startno = (pageindex - 1) * pagesize + 1;b.起始頁從0開始int endno = pageindex * pagesize;
int startno = pageindex * pagesize + 1;(2) 在row_number的同時用count計算總行數int endno = pageindex * pagesize + pagesize;
declare @page_no intdeclare @page_size
intset @page_no = 2
set @page_size = 10
;with tmpas(
select *,
row_number() over(order by id) num,
count(*) over() total
from
split_pages
)select
id, name
from
tmpwhere num between (@page_size*(@page_no-1)+1) and @page_size*@page_no
order by num
(3) 僅使用row_number計算總行數,io最少
declare @page_no intdeclare @page_size
intset @page_no = 2
set @page_size = 10
;with tmpas(
select *,
row_number() over(order by id) num,
row_number() over(order by id desc) num_desc
from
split_pages
)select id, name, num_desc + num -1
astotal
from
tmpwhere num between (@page_size*(@page_no-1)+1) and @page_size*@page_no
order by num
三. offset/fetch next
sql server 2012的新語法,類似mysql,postgresql中的liimit/offset,據稱效能比row_number又有了提公升。
declare @page_no intdeclare @page_size
intset @page_no = 3
set @page_size = 10
select *,count(*) over() as total
from split_pages
order by id
offset (@page -1) *@size rows
fetch next @size rows only;
拼接分頁查詢:
/////////
//////
分頁索引,起始頁從1開始
//////
排序字段(必傳),多欄位排序:deliverydatetime desc,sendorder,serialnumber
///desc 或 asc;多字段可將其它欄位的排序標識放在orderby,此處放預設排序
///public
static
string topagedsqlstr(string sql, int pageindex = 1, int pagesize = 1000, string orderby = "
id", string sortorder="
asc"
)
if (pagesize <= 0
)
int startno = (pageindex - 1) * pagesize + 1
;
int endno = pageindex *pagesize;
var pagedatasql =$
"select * from (select row_number() over (order by ) as tempid,* from () as datasource) as b where b.tempid between and ";
return
pagedatasql;
}public
static
string tocountsqlstr(string
sql)
) t";
}
參考文獻寫法
專著 m 集 c 報刊 n 期刊文章 j 學位 d 報告 r 專著或 集中析出的文獻 a 標準 s 專利 p 對於不屬於上述的文獻型別,採用字母 z 標識。參考文獻著錄格式 1 期刊作者 題名 j 刊名,出版年,卷 期 起止頁碼 2 專著作者 書名 m 版本 第一版不著錄 出版地 出版者,出版年 起...
mysql limit分頁查詢優化寫法
在mysql中進行分頁查詢時,一般會使用limit查詢,而且通常查詢中都會使用orderby排 序。但是在表資料量比較大的時候,例如查詢語句片段limit 10000,20,資料庫會讀取10020條資料,然後把前10000條丟棄,把最後的20條返回給你,這種消耗是可以避免的,也是沒必要的。下邊介紹幾...
oracle分頁函式寫法總結
1.根據rowid來分 select from t xiaoxi where rowid in select rid from select rownum rn,rid from select rowid rid,cid from t xiaoxi order by cid desc where r...