分页存储过程:遇到被零除错误。高手帮忙解决下。
CREATE PROCEDURE [dbo].[sp_GetPageList](
@TblName nvarchar(50) = N'',--必填:进行分页的表名
@FieldText nvarchar(1000) = N'',--选填:显示的字段,默认为 全部字段
@Pkey nvarchar(50) = N'',--必填:主键或唯一键(数值类型),推荐添加索引
@WhereText nvarchar(1000) = N'',--选填:Where 条件句
@OrderField nvarchar(100) = N'',--选填:排序字段列表,以逗号分隔
@PageIndex int = 1, --选填:显示的页码,默认值为 1
@PageSize int = 10, --选填:显示的页面大小,默认值为 10
@TotalPage int OUTPUT
)
AS
BEGIN
SET NOCOUNT ON;
-- ******************参数检查及处理:开始******************
-- 表名
IF OBJECT_ID(@TblName) IS NULL
BEGIN
RAISERROR(N'对象"%s"不存在',1,16,@TblName)
RETURN
END
IF OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsTable')=0
AND OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsView')=0
AND OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsTableFunction')=0
BEGIN
RAISERROR(N'"%s"不是表、视图或者表值函数',1,16,@TblName)
RETURN
END
-- 主键字段
IF ISNULL(@Pkey,N'')=''
BEGIN
RAISERROR(N'分页处理需要主键或唯一键(数值类型)',1,16)
RETURN
END
-- 显示字段
IF ISNULL(@FieldText,N'')=N''
SET @FieldText=N'*'
-- Where 条件句
IF ISNULL(@WhereText,N'') != N''
SET @WhereText = N' AND ' + @WhereText + N' '
-- 排序语句
IF ISNULL(@OrderField,N'') != N''
SET @OrderField = N' ORDER BY ' + @OrderField + N' '
-- 页码
IF ISNULL(@PageIndex,0)<1
SET @PageIndex=1
-- 页大小
IF ISNULL(@PageSize,0)<1
SET @PageSize=10
-- ******************参数检查及处理:结束******************
-- 计算总页数
DECLARE @selectItemsCount nvarchar(4000)
SET @SelectItemsCount = N'SELECT @TotalPage = COUNT( ' + @Pkey + N' ) FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText
EXEC sp_executesql @selectItemsCount , N'@TotalPage int OUTPUT,@Pkey nvarchar(1000),@TblName nvarchar(1000),@WhereText nvarchar(1000)'
,@TotalPage OUTPUT,@Pkey,@TblName,@WhereText
SET @TotalPage = (@TotalPage + @PageSize -1) / @PageSize
-- 计算
DECLARE @TopNForMain nvarchar(50)
DECLARE @TopNForChild nvarchar(50)
SET @TopNForMain = @PageSize
SET @TopNForChild = @PageSize * (@PageIndex - 1)
-- 返回数据集
IF @PageIndex = 1
BEGIN
DECLARE @queryStr1 nvarchar(4000)
SET @queryStr1 = N'SELECT TOP '+ @TopNForMain + N' ' + @FieldText + N' FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText + N' ' + @OrderField
EXEC sp_executesql @queryStr1
,N'@TopNForMain nvarchar(50),@FieldText nvarchar(1000),@TblName sysname,@WhereText nvarchar(1000),@OrderField nvarchar(1000)'
,@TopNForMain,@WhereText,@TblName,@FieldText,@OrderField
PRINT @queryStr1
END
ELSE
BEGIN
DECLARE @queryStr2 nvarchar(4000)
SET @queryStr2 = N'SELECT TOP ' + @TopNForMain + N' ' + @FieldText + N' FROM ' + @TblName + N' WHERE ' + @Pkey
+ N' NOT IN ( SELECT TOP ' + @TopNForChild + N' ' + @Pkey + N' FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText + N' ' + @OrderField + N' )'
+ @WhereText + @OrderField
EXEC sp_executesql @queryStr2
,N'@TopNForMain nvarchar(50),@FieldText nvarchar(1000),@TblName sysname,@Pkey nvarchar(1000),@TopNForChild nvarchar(50),@WhereText nvarchar(1000),@OrderField nvarchar(1000)'
,@TopNForMain,@FieldText,@TblName,@Pkey,@TopNForChild,@WhereText,@OrderField
PRINT @queryStr2
END
END
GO
怎么才能不出现这样的错啊
[解决办法]
SET @TotalPage = (@TotalPage + @PageSize -1) / @PageSize
只有这里一个地方是除法运算,当然在这里加了
问题是一般这种逻辑是在程序中控制的,@PageSize参数不可以<0才对
[解决办法]
CREATE PROCEDURE [dbo].[sp_GetPageList](
@TblName nvarchar(50) = N'', --必填:进行分页的表名
@FieldText nvarchar(1000) = N'', --选填:显示的字段,默认为 全部字段
@Pkey nvarchar(50) = N'', --必填:主键或唯一键(数值类型),推荐添加索引
@WhereText nvarchar(1000) = N'', --选填:Where 条件句
@OrderField nvarchar(100) = N'', --选填:排序字段列表,以逗号分隔
@PageIndex int = 1, --选填:显示的页码,默认值为 1
@PageSize int = 10, --选填:显示的页面大小,默认值为 10
@TotalPage int OUTPUT
)
AS
BEGIN
SET NOCOUNT ON;
-- ******************参数检查及处理:开始******************
-- 表名
IF OBJECT_ID(@TblName) IS NULL
BEGIN
RAISERROR(N'对象"%s"不存在',1,16,@TblName)
RETURN
END
IF OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsTable')=0
AND OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsView')=0
AND OBJECTPROPERTY(OBJECT_ID(@TblName),N'IsTableFunction')=0
BEGIN
RAISERROR(N'"%s"不是表、视图或者表值函数',1,16,@TblName)
RETURN
END
-- 主键字段
IF ISNULL(@Pkey,N'')=''
BEGIN
RAISERROR(N'分页处理需要主键或唯一键(数值类型)',1,16)
RETURN
END
-- 显示字段
IF ISNULL(@FieldText,N'')=N''
SET @FieldText=N'*'
-- Where 条件句
IF ISNULL(@WhereText,N'') != N''
SET @WhereText = N' AND ' + @WhereText + N' '
-- 排序语句
IF ISNULL(@OrderField,N'') != N''
SET @OrderField = N' ORDER BY ' + @OrderField + N' '
-- 页码
IF ISNULL(@PageIndex,0)<1
SET @PageIndex=1
-- 页大小
IF ISNULL(@PageSize,0)<1
SET @PageSize=10
-- ******************参数检查及处理:结束******************
-- 计算总页数
DECLARE @selectItemsCount nvarchar(4000)
SET @SelectItemsCount = N'SELECT @TotalPage = COUNT( ' + @Pkey + N' ) FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText
EXEC sp_executesql @selectItemsCount , N'@TotalPage int OUTPUT,@Pkey nvarchar(1000),@TblName nvarchar(1000),@WhereText nvarchar(1000)'
,@TotalPage OUTPUT,@Pkey,@TblName,@WhereText
IF(@PageSize=0)
BEGIN
SET @TotalPage = 0
END
ELSE
BEGIN
SET @TotalPage = (@TotalPage + @PageSize -1) / @PageSize
END
-- 计算
DECLARE @TopNForMain nvarchar(50)
DECLARE @TopNForChild nvarchar(50)
SET @TopNForMain = @PageSize
SET @TopNForChild = @PageSize * (@PageIndex - 1)
-- 返回数据集
IF @PageIndex = 1
BEGIN
DECLARE @queryStr1 nvarchar(4000)
SET @queryStr1 = N'SELECT TOP '+ @TopNForMain + N' ' + @FieldText + N' FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText + N' ' + @OrderField
EXEC sp_executesql @queryStr1
,N'@TopNForMain nvarchar(50),@FieldText nvarchar(1000),@TblName sysname,@WhereText nvarchar(1000),@OrderField nvarchar(1000)'
,@TopNForMain,@WhereText,@TblName,@FieldText,@OrderField
PRINT @queryStr1
END
ELSE
BEGIN
DECLARE @queryStr2 nvarchar(4000)
SET @queryStr2 = N'SELECT TOP ' + @TopNForMain + N' ' + @FieldText + N' FROM ' + @TblName + N' WHERE ' + @Pkey
+ N' NOT IN ( SELECT TOP ' + @TopNForChild + N' ' + @Pkey + N' FROM ' + @TblName + N' WHERE 1=1 ' + @WhereText + N' ' + @OrderField + N' )'
+ @WhereText + @OrderField
EXEC sp_executesql @queryStr2
,N'@TopNForMain nvarchar(50),@FieldText nvarchar(1000),@TblName sysname,@Pkey nvarchar(1000),@TopNForChild nvarchar(50),@WhereText nvarchar(1000),@OrderField nvarchar(1000)'
,@TopNForMain,@FieldText,@TblName,@Pkey,@TopNForChild,@WhereText,@OrderField
PRINT @queryStr2
END
END
GO
[解决办法]
你不清楚哪里需要除0?这不是你自己写的吗?我都在用2012了.....2000的样子都快记不得了。
[解决办法]
@PageSize不是传过去的参数吗,按理说不应该出现<1的情况啊
[解决办法]
关闭除零错误,遇除零则返回NULL
set arithabort off
set ansi_warnings off