网络工作室暑假后第三次培训资料(几种SQL分页的总结)整理

简介:

在实际开发的过程中如果记录数非常的庞大,如果直接用SQL语句查询并填充到DataTable中,将是一件非常恐怖的事情。而且对网站性能,服务器性能消耗很大。

两个常犯的错误:

1)在现实数据时,查询时会将所有的满足条件的数据全部填充到DataTable中,然后在程序中根据条件显示其中的一部分数据。

2)在统计数据时,在获取符合条件的记录条数时也是通过将所有满足条件的数据全部填充到DataTable中,然后通过DataTable实例Rows.Count属性来获取记录条数。

这样做的结果就是效率极低,如果数据量太大,可能造成自己需要的数据长久的无法显示,所以显示数据是应该使用分页查询。分页查询就是每次只返回所需要的数据,而不用每次都从数据库中把数据全部提出来,这样可以降低程序与数据库之间的数据传送量,并且还可以提高程序的性能。

一般来说,在数据量大的情况下要分页显示,这样决定返回的查询结果集的参数有两个:当前显示的页数pageIndex和每页显示的记录条数size。

所使用的数据表如下图:表中的id是主键。

下面我们按照id正序排列查询所有人的信息,SQL语句如下:


 
 
  1. select * from T_Person orderby id ASC;

现在我们对数据进行分页,分页规则就是,页容量5条数据,那么我们完成第1页的数据查询可以使用SQL语句是


  
  
  1. selecttop 5 * from T_Person orderby id asc;

这样我们就可以取出第1页所要显示的5条数据。但是我们应该怎么样编写SQL语句才可以显示第2,3,4......页的数据呢?

如果说我们第1页取出的数据时第1-5条记录,那么第2页的数据就应该是6-10的记录。我们应该怎么做到呢?有两种方法:第一种就是一次性的将所有的数据都提取出填充到DataTable中,然后在for循环中通过i从5开始,并且i小于10这种方法显示数据,这种方法的缺点前面已经介绍。第二种方法就是在数据库中对数据进行过滤,这个时候SQL语句中的 not in 就可以很好地排上用场。

那么怎么使用not in将第2页的数据显示出来呢,SQL语句如下:


   
   
  1. selecttop 5 * from T_Person where id notin

  2. (

  3. selecttop 5 id from T_Person orderby id asc

  4. )orderby id asc;

在这里使用了一个子查询先将第1页的数据编号显示出来,然后使用not in 将1-5的记录从数据中排出,显示的就是6-10 的数据记录。

因为数据id是从1开始,所以id为1-5的记录显示在第1页,id为6-10的记录在第2页显示,id为11-15的记录在第3页显示,依此类推第n页的数据的SQL语句是:n为定义显示数据的第几页,


    
    
  1. selecttop 5 * from T_Person where id notin

  2. (

  3. selecttop (n-1)5 id from T_Person orderby id asc

  4. )orderby id asc;

这样就可以根据参数n显示第几页的数据。

还有一个比较重要的知识点就是如何计算数据页分页的总数,如果现在有20条数据,如果每页5条数据,很明显就是分4页。但是如果记录数是21条,这个时候很明显应该分5页。有一个公式,假如总共有m条数据,每页显示n条数据(m,n都大于0),那么需要显示所有记录的页数page为:page=(m%n)==0?(m/n):(m/n+1);

第二种分页的方法:

这里需要使用SQL中的ROW_NUMBER函数,该函数的作用就是在返回的记录集合内为每一条记录标上顺序编号。

因为我们要对数据库进行删除操作的话,数据库表中的id的值可能是不连续的。因为在上面的方法中,我们主要是使用id来排序,不需要太多的操作,但是下面的方法,就需要有一个连续的id值来查询数据。

先看一个SQL语句:


    
    
  1. select * from

  2. (

  3. select * from T_Person

  4. )as a

  5. where id>5 and id<=10

这样的话,我们仍然能够按照要求取出相应页数的数据。我们只需要稍微改变一下,SQL语句如下:n为显示数据的页码


     
     
  1. select * from

  2. (

  3. select * from T_Person

  4. )as a

  5. where id>(n-1)*5 and id<=n*5

这个时候我们就可以根据参数n来选出相应页数的数据,但是我们可以很快的发现,这个分页对id的连续有很大的依赖性,所以,我们在对数据进行删除操作的时候,数据库中的id很可能是不连续的,所以在数据库中进行分页的时候,就需要对数据进行编号,这个时候就要使用SQl中的ROW_NUMBER函数,

使用ROW_NUMBER函数查询的SQl语句和显示结果如下:

很容易的我们发现在id的前面有了一个按照id正序排列的rl的列。

所以,完整的 SQL分页语句为:n为我们传入的分页的页码,默认的每页显示的数据位5条


    
    
  1. select * from

  2. (

  3. select * from T_Person

  4. )as a

  5. where id>(n-1)*5 and id<=n*5

这样,我们就可以建立相应的分页存储过程,在数据库中对数据进行分页,然后供程序进行调用。

最后分享一个,在网上看到的一个比较好的分页存储过程:



     
     
  1. createPROCEDURE GetPageData

  2. (

  3. @TableName varchar(30),--表名称

  4. @IDName varchar(20),--表主键名称

  5. @PageIndex int,--当前页数

  6. @PageSize int--每页大小

  7. )

  8. AS

  9. IF @PageIndex > 0

  10. BEGIN

  11. set nocount on

  12. DECLARE @PageLowerBound int,@StartID int,@sql nvarchar(225)

  13. SET @PageLowerBound = @PageSize * (@PageIndex-1)

  14.   IF @PageLowerBound<1

  15. SET @PageLowerBound=1

  16. SET ROWCOUNT @PageLowerBound

  17. SET @sql=N'SELECT @StartID = ['+@IDName+'] FROM '+@TableName+' ORDER BY '+@IDName

  18. exec sp_executesql @sql,N'@StartID int output',@StartID output

  19. SET ROWCOUNT 0

  20. SET @sql='select top '+str(@PageSize) +' * from '+@TableName+' where ['+@IDName+']>='+ str(@StartID) +' ORDER BY ['+@IDName+'] '

  21. EXEC(@sql)

  22. set nocount off

  23. END


本文转自yisuowushinian 51CTO博客,原文链接:http://blog.51cto.com/yisuowushinian/1034882 ,如需转载请自行联系原作者



相关文章
|
7月前
|
机器学习/深度学习 分布式计算 资源调度
【社交网络分析】课程考试复盘 + 相关资料补充
【社交网络分析】课程考试复盘 + 相关资料补充
104 0
|
SQL Java 数据库连接
Mybatis-动态sql和分页
Mybatis-动态sql和分页
168 0
|
SQL XML Java
【MyBatis】动态SQL和mybatis分页的运用
如果我们的前台没有传参,比如没有传入我们的name值,name就会把字段值改为null,这就违背了我们编码的初衷。许多人会使用类似于where 1 = 1来作为前缀,在代码中会用if,再用and进行一个sql拼接。
|
1月前
|
SQL 缓存 Java
【详细实用のMyBatis教程】获取参数值和结果的各种情况、自定义映射、动态SQL、多级缓存、逆向工程、分页插件
本文详细介绍了MyBatis的各种常见用法MyBatis多级缓存、逆向工程、分页插件 包括获取参数值和结果的各种情况、自定义映射resultMap、动态SQL
【详细实用のMyBatis教程】获取参数值和结果的各种情况、自定义映射、动态SQL、多级缓存、逆向工程、分页插件
|
4月前
|
SQL 关系型数据库 MySQL
SQL中如何实现分页?
【8月更文挑战第3天】SQL中如何实现分页?
148 36
|
安全 物联网 云栖大会
2023云栖大会 | 云网络技术Session主题资料和视频回放归档(已完结)
2023年10月31日,杭州,一年一度的云栖大会如期而至;阿里云飞天洛神云网络作为阿里云计算的连接底座,是飞天云操作系统的核心组件,致力于为上云企业提供高可靠、高性能、高弹性、智能的连接服务。本次云栖,云网络产品线也带来全系列产品升级,以及创新技术重磅解读,共包括1个Keynote,22个Session,包括产品发布、Deep Dive、最佳实践、客户分享、开放生态等多维度全面解读云网络进展。
2252 7
|
6月前
|
SQL 安全 数据库连接
sql如何访问网络数据库
访问网络数据库(通常指的是不在本地计算机上而是在网络上的数据库服务器)的SQL操作,其实与访问本地数据库在SQL语句的编写上并没有太大差异。主要的区别在于连接的设置和配置,以及如何确保网络连接的安全性
|
6月前
|
SQL 缓存 Java
Java框架之MyBatis 07-动态SQL-缓存机制-逆向工程-分页插件
Java框架之MyBatis 07-动态SQL-缓存机制-逆向工程-分页插件
|
7月前
|
SQL 编译器 网络安全
【网络安全 | SQL注入】一文讲清预编译防御SQL注入原理
【网络安全 | SQL注入】一文讲清预编译防御SQL注入原理
414 0
|
7月前
|
SQL 人工智能 运维
数据库基础入门 — SQL排序与分页
数据库基础入门 — SQL排序与分页
56 0
下一篇
DataWorks