注:INSERT INTO SELECT 在已有identity列时会报错,以下存储过程直接读取结构,所以不会
CREATE
PROCEDURE
TablePage
(
@TableName
nvarchar
(
255
),
--
表名
@OrderStr
nvarchar
(
500
),
--
排序字段
@PageNumber
int
,
--
当前页
@PageSize
int
--
每页记录数
)
AS
DECLARE
@sqlstr
nvarchar
(
4000
)
DECLARE
@sqlins
nvarchar
(
1500
)
--
导入数据至临时表时用SQL
DECLARE
@sqljoin
nvarchar
(
2000
)
--
连接显示数据用SQL
DECLARE
@sqlpage
nvarchar
(
200
)
--
分页计算
DECLARE
@TableId
int
--
表ID
DECLARE
@IndexId
int
--
主键约束ID
DECLARE
@RowCount
int
--
表中数据条数
DECLARE
@BegNumber
int
--
起始记录
DECLARE
@EndNumber
int
--
截止记录
DECLARE
@MaxPage
int
--
最大页
DECLARE
@KeyName
sysname
--
主键字段名
DECLARE
@KeyType
sysname
--
主键字段类型
DECLARE
@KeyPrec
smallint
--
主键栏位为变长时长度
DECLARE
@KeyScale
tinyint
--
主键栏位精度
IF
@PageNumber
<=
0
SET
@PageNumber
=
1
IF
@PageSize
<=
0
SET
@PageSize
=
1
SET
@TableId
=
OBJECT_ID
(
@TableName
)
IF
@TableId
IS
NULL
BEGIN
RAISERROR
(
'
表名或对象名不存在当前数据库中,请检查
'
,
16
,
1
)
RETURN
END
--
取得总记录数
SET
@sqlstr
=
'
SELECT @iRowCount=COUNT(*) FROM
'
+
@TableName
EXEC
SP_EXECUTESQL
@sqlstr
, N
'
@iRowCount int OUTPUT
'
,
@RowCount
OUTPUT
--
取得主键
DECLARE
cur
CURSOR
STATIC
FOR
SELECT
C.name KeyName, T.name KeyType, C.prec, C.scale
FROM
syscolumns C
LEFT
JOIN
sysindexes I
ON
I.id
=
C.id
LEFT
JOIN
systypes T
ON
T.xtype
=
C.xtype
WHERE
C.id
=
@TableId
AND
(I.status
&
0x800
)
=
0x800
AND
(
C.name
=
index_col
(
@TableName
, I.indid,
1
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
2
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
3
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
4
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
5
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
6
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
7
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
8
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
9
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
10
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
11
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
12
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
13
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
14
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
15
)
OR
C.name
=
index_col
(
@TableName
, I.indid,
16
)
)
OPEN
cur
IF
@@CURSOR_ROWS
<=
0
BEGIN
RAISERROR
(
'
指定表中不存在主键,请检查
'
,
16
,
1
)
RETURN
END
--
存在主键,创建同样主键临时表
FETCH
next
FROM
cur
INTO
@KeyName
,
@KeyType
,
@KeyPrec
,
@KeyScale
SET
@sqlstr
=
'
CREATE TABLE #TMP(ROW_NUMBER INT IDENTITY(1, 1)
'
SET
@sqlins
=
''
SET
@sqljoin
=
''
WHILE
(
@@FETCH_STATUS
=
0
)
BEGIN
--
插入SQL
IF
@sqlins
<>
''
SET
@sqlins
=
@sqlins
+
'
,
'
SET
@sqlins
=
@sqlins
+
@KeyName
--
连接SQL
IF
@sqljoin
<>
''
SET
@sqljoin
=
@sqljoin
+
'
AND #TMP.
'
+
@KeyName
+
'
=
'
+
@TableName
+
'
.
'
+
@KeyName
ELSE
SET
@sqljoin
=
@sqljoin
+
'
LEFT JOIN
'
+
@TableName
+
'
ON #TMP.
'
+
@KeyName
+
'
=
'
+
@TableName
+
'
.
'
+
@KeyName
SET
@sqlstr
=
@sqlstr
+
'
,
'
+
@KeyName
+
'
'
+
@KeyType
--
定义主键类型及长度
IF
@KeyType
=
'
binary
'
OR
@KeyType
=
'
char
'
OR
@KeyType
=
'
nchar
'
OR
@KeyType
=
'
nvarchar
'
OR
@KeyType
=
'
varbinary
'
OR
@KeyType
=
'
varchar
'
BEGIN
--
类型是可变长度,无精度时,取prec栏位
--
不定长,无精度的包括: binary(173), char(175), nchar(239),nvarchar(231), varbinary(165), varchar(167)
SET
@sqlstr
=
@sqlstr
+
'
(
'
+
CAST
(
@KeyPrec
AS
nvarchar
)
+
'
)
'
END
ELSE
IF
@KeyType
=
'
decimal
'
OR
@KeyType
=
'
numeric
'
BEGIN
--
类型是可变长度且拥有精度时,取prec栏位+','+scale栏位
--
不定长,有精度的包括: decimal(106), numeric(108)
SET
@sqlstr
=
@sqlstr
+
'
(
'
+
CAST
(
@KeyPrec
AS
nvarchar
)
+
'
,
'
+
CAST
(
@KeyScale
AS
nvarchar
)
+
'
)
'
END
--
其它类型是定长类型时,无须指定长度
FETCH
next
FROM
cur
INTO
@KeyName
,
@KeyType
,
@KeyPrec
,
@KeyScale
END
CLOSE
cur
DEALLOCATE
cur
SET
@sqlstr
=
@sqlstr
+
'
)
'
--
插入SQL
SET
@sqlins
=
'
INSERT INTO #TMP(
'
+
@sqlins
+
'
) SELECT
'
+
@sqlins
+
'
FROM
'
+
@TableName
--
计算页面
SET
@MaxPage
=
CAST
(
@RowCount
/
@PageSize
AS
INT
)
IF
@RowCount
%
@PageSize
>
0
SET
@MaxPage
=
@MaxPage
+
1
IF
@MaxPage
=
0
SET
@MaxPage
=
1
IF
@PageNumber
>
@MaxPage
SET
@PageNumber
=
@MaxPage
SET
@BegNumber
=
(
@PageNumber
-
1
)
*
@PageSize
+
1
SET
@EndNumber
=
@PageNumber
*
@PageSize
SET
@sqlpage
=
'
WHERE #TMP.ROW_NUMBER BETWEEN
'
+
CAST
(
@BegNumber
AS
nvarchar
)
+
'
AND
'
+
CAST
(
@EndNumber
AS
nvarchar
)
--
连接SQL
SET
@sqljoin
=
'
SELECT #TMP.ROW_NUMBER,
'
+
@TableName
+
'
.* FROM #TMP
'
+
@sqljoin
--
整合SQL
SET
@sqlstr
=
@sqlstr
+
'
'
+
@sqlins
+
'
'
+
@sqljoin
+
@sqlpage
--
加上删除命令
SET
@sqlstr
=
@sqlstr
+
'
DROP TABLE #TMP
'
EXEC
(
@sqlstr
)
--TablePage 'TableName','',39,17