分页,大家很非常熟悉的内容,不会上网的小朋友都知道;咱们看书的时候,就有了分页,其实我个人觉得,网站对内容的分页,其实也是根据书上的这个分页设想出来的,觉得一页的内容太多了,应该分页出来,给人不一样的感觉。其实我们写文章的分段也是一样,分段要多点,让读者很快就能阅读完一段,这对读者的心理上来说,是一个很大心理成就,相信大家也不愿意看到一篇文章过来,密密麻麻的,找不到分段,那这样的文章,我想是卖不出去的。也就是只能留着自己看了,也许自己也不敢看。
那么站在用户的角度来想,那这个分页是必须要有的,除非你确定你的内容能最多在鼠标划一下就能看完的内容之内(其实我是试着去看了一下百度,百度是鼠标滑下来一点点就能看到下面的分页序列了,也许对于别的分辨率不一样,但是也差不多吧)。我们看看一些比较厉害的搜索引擎:
我总感觉这个效果特别好,这样大家都不用数里边有多少个O了,第一次用google的时候,就喜欢上了这个,分页都做的设置的这么别致;当然百度也不错:
这看起来很普通,其实很多网站都差不多是这样的普通的分页,给用户一种熟悉的感觉,也挺好;CSDN也是一样:
那么我们今天也来试着模拟这个分页:
假分页:从数据库中选择所有的记录后再进行分页。
使用GridView控件来达到分页的功能:
我们在test1.aspx里边拖进来一个GridView控件:
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="test1.aspx.cs" Inherits="WebApplication1.test1" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head runat="server"> <title>分页测试</title> </head> <body> <form id="form1" runat="server"> <asp:GridView ID="GridView1" runat="server" AllowPaging="True" onpageindexchanging="GridView1_PageIndexChanging" PageSize="5"> </asp:GridView> </form> </body> </html>我们进行一下数据的绑定。
/* *创建人:陈宗毅 *创建时间:2012年8月24日 */ using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.UI; using System.Web.UI.WebControls; using BLL; namespace WebApplication1 { public partial class test1 : System.Web.UI.Page { protected void Page_Load(object sender, EventArgs e) { if (!Page.IsPostBack ) { BindNews(); } } private void BindNews() { GridView1.DataSource = new B_Page().SelectAll(); GridView1.DataBind(); } protected void GridView1_PageIndexChanging(object sender, GridViewPageEventArgs e) { GridView1.PageIndex = e.NewPageIndex; BindNews(); } } }我们还要设置一下GridView的一些属性:
那么我们来看看这个效果,前提是数据库里边咱们要有数据让代码来读取。
这样我们就轻而易举的实现了分页的功能。他的一个非常大的优点就是设计简单,除了绑定就剩两句话而已;但是这个缺点也是很明显的,咱们这个SelectAll是选择全部的新闻,那么这个分页是每次分页都选择出全部的新闻,咱们做的这个测试是几条新闻而已,要是真正发布的系统,新闻数量就达到几万条甚至几十万条,那么每次分页都要选择出全部的新闻,那整个系统就会显得特别特别的慢,就会导致用户无法忍受你选择新闻所花费的时间,这种分页方式:把数据从数据库中全部选择出来,然后再进行分页;这种分页就是咱们经常说的,假分页。
真分页:只从数据中选择当前页的记录。换句话说:我们想要什么就拿什么,避免了多拿的现象。
我们先看一下这个控件怎么使用:AspNetPager
我们来看看这边的代码:
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="test1.aspx.cs" Inherits="WebApplication1.test1" %> <%@ Register assembly="AspNetPager" namespace="Wuqi.Webdiyer" tagprefix="webdiyer" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head runat="server"> <title>分页测试</title> </head> <body> <form id="form1" runat="server"> <webdiyer:AspNetPager ID="anp" runat="server" onpagechanged="anp_PageChanged" PageSize="5"> </webdiyer:AspNetPager> </form> </body> </html>
我们让他显示一下记录数:
/* *创建人:陈宗毅 *创建时间:2012年8月24日 */ using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.UI; using System.Web.UI.WebControls; using BLL; namespace WebApplication1 { public partial class test1 : System.Web.UI.Page { protected void Page_Load(object sender, EventArgs e) { if (!Page.IsPostBack ) { anp.RecordCount = 22; } } protected void anp_PageChanged(object sender, EventArgs e) { Response.Write("开始记录数:"+anp.StartRecordIndex+"<br>结束记录数:"+anp.EndRecordIndex); } } }
那么效果是这样的:
然后剩下的就是导入咱们的数据库内容了,但是我们遇到了一个问题,看看我们的数据库:
我们看到这里的id和序号是不对应的,那么我们分页需要的是序号,那么我们必须想办法把序号提前出来,那么我们的数据库有了这么一种办法,我们看看:
select ROW_NUMBER() over (order by id desc)as 行号, * from news那么我们再来看看这个效果:
这个效果就是我们把那个序号提取出来了,就是行号。
那么我们要取6~10条记录,我们在数据库这么写:
with temptabl as( select ROW_NUMBER() over (order by id desc)as 行号, * from news ) select * from temptabl where 行号 between 5 and 10我们就能把5~10条记录提取出来了:
这也就差不多完成了。我们接下来写一个存储过程:
create PROCEDURE [dbo].[proc_FenYE] @tblName varchar(255), -- 表名 @strGetFields varchar(1000) = '*', -- 需要返回的列,默认* @strOrder varchar(255)='', -- 排序的字段名,必填 @strOrderType varchar(10)='ASC', -- 排序的方式,默认ASC @PageSize int = 10, -- 页尺寸,默认10 @PageIndex int = 1, -- 页码,默认1 @strWhere varchar(1500) = '' -- 查询条件 (注意: 不要加 where) AS declare @strSQL varchar(5000) if @strWhere !='' set @strWhere=' where '+@strWhere set @strSQL= 'SELECT * FROM ('+ 'SELECT ROW_NUMBER() OVER (ORDER BY '+@strOrder+' '+@strOrderType+') AS pos,'+@strGetFields+' '+ 'FROM '+@tblName+' '+@strWhere+ ') AS sp WHERE pos BETWEEN '+str((@PageIndex-1)*@PageSize+1)+' AND '+str(@PageIndex*@PageSize) exec (@strSQL) GO那么我们的SQLhelper里边:
/// <summary> 返回执行的SQL语句的第一行第一列的值 /// /// </summary> /// <param name="sql">SQL语句</param> /// <returns></returns> public string ExecuteScalar(string sql) { try { cmd = new SqlCommand(sql, GetConn()); object obj = cmd.ExecuteScalar(); if (obj != null) { return obj.ToString(); } return ""; } catch (Exception ex) { throw ex; } finally { if (conn.State == ConnectionState.Open) { conn.Close(); } } }我们的DAL里边写一个FenYeDAO:
/// <summary>根据条件计算新闻记录数 /// /// </summary> /// <param name="cond">条件,不用加where</param> /// <returns></returns> public int CalcCount(string cond) { string sql = "select count(*) from news"; if (!string.IsNullOrEmpty(cond)) { sql += "where" + cond; } return int.Parse( sqlhelper.ExecuteScalar(sql)); }BLL里边:FenYeManager.cs:
/// <summary>根据条件计算新闻记录数 /// /// </summary> /// <param name="cond">条件,不用加where</param> /// <returns></returns> public int CalcCount(string cond) { return ndao.CalcCount(cond); }我们在测试文件里边test.aspx:
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="test1.aspx.cs" Inherits="WebApplication1.test" %> <%@ Register Assembly="AspNetPager" Namespace="Wuqi.Webdiyer" TagPrefix="webdiyer" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head runat="server"> <title>分页测试</title> <link href="css/pager.css" rel="stylesheet" type="text/css" /> </head> <body> <form id="form1" runat="server"> <div> <asp:GridView ID="GridView1" runat="server"> </asp:GridView> <webdiyer:AspNetPager ID="anp" runat="server" PageSize="5" OnPageChanged="anp_PageChanged" CustomInfoHTML="总计%RecordCount%条记录,共%PageCount%页" FirstPageText="首页" LastPageText="尾页" NextPageText="下一页" PrevPageText="上一页" ShowCustomInfoSection="Left" ShowPageIndexBox="Never" CssClass="pages" CurrentPageButtonClass="cpb" > </webdiyer:AspNetPager> </div> </form> </body> </html>在后台test.aspx.cs代码里边绑定一下:
/* *创建人:陈宗毅 *创建时间:2012年8月24日 */ using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.UI; using System.Web.UI.WebControls; using BLL; namespace WebApplication1 { public partial class test : System.Web.UI.Page { BLL.NewsManager nm = new BLL.NewsManager(); protected void Page_Load(object sender, EventArgs e) { if (!Page.IsPostBack ) { anp.RecordCount = nm.CalcCount("") ; BindGV(); } } //分页事件 protected void anp_PageChanged(object sender, EventArgs e) { BindGV(); } //绑定新闻列表 private void BindGV() { int pagesize = anp.PageSize; int pageindex = anp.CurrentPageIndex; GridView1.DataSource = nm.Select(pagesize, pageindex, ""); GridView1.DataBind(); } } }最后我们加上那个迅雷的风格,那么效果如下:
呵呵,其实分页也没那么难,对自己有信心,就能做好。
- 9楼shutingwang1小时前
- 不错,继续加油
- Re: yi_zz1小时前
- 回复shutingwangn一起加油~
- 8楼lfsfxy91小时前
- select ROW_NUMBER() over (order by id desc)as 行号, * from news
- Re: yi_zz1小时前
- 回复lfsfxy9n明白,这里是为了突出。
- 7楼beijiguangyong昨天 22:33
- 对自己有信心,就能做好。
- Re: yi_zz1小时前
- 回复beijiguangyongnnice~
- 6楼zs15932616453昨天 21:44
- 顶一个
- Re: yi_zz昨天 22:00
- 回复zs15932616453n常来啊~
- 5楼SCAUSCNU昨天 20:50
- 不错,到时应该要用到
- Re: yi_zz昨天 21:36
- 回复SCAUSCNUn恩,希望对大家有所帮助。
- 4楼dandanzmc昨天 20:39
- 你这的好东西特多
- Re: yi_zz昨天 20:40
- 回复dandanzmcnO(∩_∩)O~
- 3楼lbq613613昨天 19:36
- 再多来点解释啥的,不知道是不是我就能看懂了···哈哈
- Re: yi_zz昨天 20:37
- 回复lbq613613n你一定能看懂,不难的
- 2楼lfsfxy9昨天 19:26
- 可以啊,很棒!
- Re: yi_zz昨天 19:27
- 回复lfsfxy9n常来哦
- 1楼shehun1昨天 19:14
- ASPNETPAGER,一个不错的分页控件
- Re: yi_zz昨天 19:16
- 回复shehun1n恩,感觉不错。