SQL SERVER 分页处理,自动识别标准SQL语句并生成适合分页的SQL语句
来源:互联网 发布:西方马克思主义 知乎 编辑:程序博客网 时间:2024/06/10 00:17
/// <summary>
/// SQL SERVER 分页处理,自动识别标准SQL语句并生成适合分页的SQL语句
/// </summary>
public class SQLPage
{
public SQLPage()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
/// <summary>
/// 生成SQL分页语句,记录总数为0表示生成统计语句
/// </summary>
/// <param name="strSQLInfo">原始SQL语句</param>
/// <param name="strWhere">在分页前要替换的字符串,用于分页前的筛选</param>
/// <param name="PageSize">页大小</param>
/// <param name="PageNumber">页码</param>
/// <param name="AllCount">记录总数</param>
/// <returns>生成SQL分页语句</returns>
public static string MakeSQLStringByPage(string strSQLInfo,string strWhere,int PageSize,int PageNumber,int AllCount)
{
string strSQLType=string.Empty ;
if(AllCount!=0)
{
if(PageNumber==1) //首页
{
strSQLType="First";
}
else if(PageSize*PageNumber>AllCount) //最后的页 @@LeftSize
{
PageSize=AllCount-PageSize*(PageNumber-1);
strSQLType="Last";
}
else //中间页
{
strSQLType="Mid";
}
}
else //特殊处理
{
strSQLType="Count";
}
string SQL=MakeSQLStringByPage( strSQLInfo, strSQLType);
//执行分页参数替换
SQL=SQL.Replace ("@@PageSize",PageSize.ToString ())
.Replace ("@@Page_Size_Number",Convert.ToString (PageSize * PageNumber))
.Replace ("@@LeftSize",PageSize.ToString ())
.Replace ("@@Where",strWhere);
return SQL;
}
private static string MakeSQLStringByPage(string strSQLInfo,string strSQLType)
{
#region SQL 复杂度分析
//SQL 复杂度分析 开始
bool SqlFlag=true;//简单SQL标记
string TestSQL=strSQLInfo.ToUpper ();
int n=TestSQL.IndexOf ("SELECT ",0);
n=TestSQL.IndexOf ("SELECT ",n+7);
if(n==-1)
{
//可能是简单的查询,再次处理
n=TestSQL.IndexOf (" JOIN ",n+7);
if(n!=-1) SqlFlag=false;
else
{
//判断From 谓词情况
n=TestSQL.IndexOf("FROM ",9);
if(n==-1) return "";
//计算 WHERE 谓词的位置
int m=TestSQL.IndexOf ("WHERE ",n+5);
// 如果没有WHERE 谓词
if(m==-1) m=TestSQL.IndexOf ("ORDER BY ",n+5);
//如果没有ORDER BY 谓词,那么无法排序,退出;
if(m==-1) return "";
string strTableName=TestSQL.Substring (n,m-n);
//表名中有 , 号表示是多表查询
if(strTableName.IndexOf (",")!=-1)
SqlFlag=false;
}
}
else
{
//有子查询;
SqlFlag=false;
}
//SQL 复杂度分析 结束
#endregion
#region 排序语法分析
//排序语法分析 开始
int iOrderAt=strSQLInfo.ToLower ().LastIndexOf ("order by ");
//如果没有ORDER BY 谓词,那么无法排序分页,退出;
if(iOrderAt==-1) return "";
string strOrder=strSQLInfo.Substring (iOrderAt+9);
strSQLInfo=strSQLInfo.Substring(0,iOrderAt);
string[] strArrOrder=strOrder.Split (new char []{','});
for(int i=0;i<strArrOrder.Length ;i++)
{
string[] strArrTemp=(strArrOrder[i].Trim ()+" ").Split (new char[]{' '});
//压缩多余空格
for(int j=1;j<strArrTemp.Length ;j++)
{
if(strArrTemp[j].Trim ()=="")
{
continue;
}
else
{
strArrTemp[1]=strArrTemp[j];
if(j >1 ) strArrTemp[j]="";
break;
}
}
//判断字段的排序类型
switch(strArrTemp[1].Trim ().ToUpper ())
{
case "DESC":
strArrTemp[1]="ASC";
break;
case "ASC":
strArrTemp[1]="DESC";
break;
default:
//未指定排序类型,默认为降序
strArrTemp[1]="DESC";
break;
}
//消除排序字段对象限定符
if(strArrTemp[0].IndexOf (".")!=-1)
strArrTemp[0]=strArrTemp[0].Substring (strArrTemp[0].IndexOf (".")+1);
strArrOrder[i]=string.Join (" ",strArrTemp);
}
//生成反向排序语句
string strNewOrder=string.Join (",",strArrOrder).Trim ();
strOrder=strNewOrder.Replace ("ASC","ASC0").Replace ("DESC","ASC").Replace ("ASC0","DESC");
//排序语法分析结束
#endregion
#region 构造分页查询
string SQL=string.Empty ;
if(!SqlFlag)
{
//复杂查询处理
switch(strSQLType.ToUpper ())
{
case "FIRST":
SQL="Select Top @@PageSize * FROM (/n" +strSQLInfo+
"/n) T0 @@Where ORDER BY "+strOrder;
break;
case "MID":
SQL=@"SELECT Top @@PageSize * FROM
(SELECT Top @@PageSize * FROM
(
SELECT Top @@Page_Size_Number * FROM (";
SQL+="/n"+strSQLInfo+" ) P_T0 @@Where ORDER BY "+strOrder+"/n";
SQL+=@") P_T1
ORDER BY "+ strNewOrder +") P_T2 /n"+
"ORDER BY "+strOrder;
break;
case "LAST":
SQL=@"SELECT * FROM (
Select Top @@LeftSize * FROM ("+"/n/r"+strSQLInfo+"/r";
SQL+=" ) P_T0 @@Where ORDER BY "+ strNewOrder+"/n/r"+
" ) P_T1 ORDER BY "+strOrder;
break;
case "COUNT":
SQL="Select COUNT(*) FROM ( " +strSQLInfo+" ) P_Count @@Where";
break;
default:
SQL=strSQLInfo+strOrder;//还原
break;
}
}
else
{
//简单查询处理
switch(strSQLType.ToUpper ())
{
case "FIRST":
SQL=strSQLInfo.ToUpper().Replace ("SELECT ","SELECT TOP @@PageSize ");
SQL+=" @@Where ORDER BY "+strOrder;
break;
case "MID":
string strRep=@"SELECT Top @@PageSize * FROM
(SELECT Top @@PageSize * FROM
(
SELECT Top @@Page_Size_Number ";
SQL=strSQLInfo.ToUpper().Replace ("SELECT ",strRep);
SQL+=" @@Where ORDER BY "+strOrder;
SQL+=" /r/n) P_T0 ORDER BY "+ strNewOrder+"/n/r"+
" ) P_T1 ORDER BY "+strOrder;
break;
case "LAST":
string strRep2=@"SELECT * FROM (
Select Top @@LeftSize ";
SQL=strSQLInfo.ToUpper().Replace ("SELECT ",strRep2);
SQL+=" @@Where ORDER BY "+ strNewOrder+"/n/r"+
" ) P_T1 ORDER BY "+strOrder;
break;
case "COUNT":
SQL="Select COUNT(*) FROM ( " +strSQLInfo+" ) P_Count @@Where";
break;
default:
SQL=strSQLInfo+strOrder;//还原
break;
}
}
return SQL;
#endregion
}
}
- SQL SERVER 分页处理,自动识别标准SQL语句并生成适合分页的SQL语句
- SQL Server 分页语句
- SQL Server分页语句
- sql server 分页语句
- SQL Server 分页语句
- Sql Server分页语句
- sql Server SQL分页语句
- 分页的sql语句
- 分页语句 mysql 、server sql、oracle的分页语句
- sql server分页语句整理
- sql server,oracle,mysql的分页语句
- 一个高效率的SQL Server分页语句
- ms sql server分页sql语句
- SQL语句分页 SQL Server 2000/2005
- 关于SQL Server SQL语句查询分页数据的解决方案
- 最优化的ms sql server分页sql语句
- 关于SQL Server SQL语句查询分页数据的解决方案
- 优化的ms sql server分页sql语句
- 使用SharpZip压缩与解压缩的实战经验
- .NET Framework 2.0 中新增的两个压缩类
- WinRAR命令行参数
- 书评--设计模式入门
- WinRar 使用方法参数设置
- SQL SERVER 分页处理,自动识别标准SQL语句并生成适合分页的SQL语句
- Dojo学习笔记(6. dojo.io.IO & dojo.io.BrowserIO)
- 项目管理中的问题
- 关于薪资问题你应该知道的
- spring.net 学习一
- little endian and big endian(zz)
- 神州数码客户端alpha3版发布[神州数码认证客户端破解]
- MEPG,DAT转rmvb最好的工具 Easy RealMedia Producer应用要领
- Linux手机DIY.库文件专题.交叉编译的浮点问题