在尝试理解动态SQL的过程中,我尝试通过从sys.tables
的每个表中动态插入行数的计数来开始简单。
这是我的代码:
SELECT
Name, ROW_NUMBER() OVER (ORDER BY NEWID() ) AS SomeNumb
INTO
#Dyn
FROM
sys.tables
CREATE TABLE ##Results (Cnt INT)
DECLARE @Table NVARCHAR(100)
DECLARE @Counter INT
SET @Counter = 1
SET @Table = (SELECT Name FROM #Dyn WHERE SomeNumb = @Counter)
DECLARE @Sql NVARCHAR(1000)
WHILE @Counter <= (SELECT COUNT(*) FROM #Dyn)
BEGIN
INSERT INTO ##ResultsTable
SELECT @Sql = 'SELECT COUNT(*) AS Cnt FROM #Dyn WHERE
Name = ' + @Table + 'AND SomeNumb = ' + @Counter
EXECUTE (@Sql)
SET @Counter = @Counter + 1
SET @Sql = ''
END
SELECT * FROM ##ResultsTable
唯一的好处是不会出错。虽然这可能会给我一些指导。我知道我的ResultsTable
存在范围问题,但是我认为使用##
而不是#可以解决此问题。
任何指针都将受到高度赞赏。
答案 0 :(得分:1)
一种方法不是使用WHILE
或sys.tables
循环,而是使用sys.schemas
和FOR XML PATH
和DECLARE @SQL nvarchar(MAX);
SET @SQL = (SELECT N'SELECT ''' + QUOTENAME(s.[name]) + N'.' + QUOTENAME(t.name) +''' AS ObjectName, COUNT(*) AS [RowCount]' + NCHAR(10) +
N'FROM ' + QUOTENAME(s.[name]) + N'.' + QUOTENAME(t.[name]) + N';' + NCHAR(10)
FROM sys.tables t
JOIN sys.schemas s ON t.SCHEMA_ID = s.SCHEMA_ID
FOR XML PATH(N''))
PRINT @SQL;
CREATE TABLE #Cnt (ObjectName sysname, [RowCount] int);
INSERT INTO #Cnt (ObjectName, [RowCount])
EXEC sp_executesql @SQL;
SELECT *
FROM #cnt;
DROP TABLE #cnt;
:
sp_msforeachtable
或者,您可以使用未记录的过程CREATE TABLE #Cnt (ObjectName sysname, [RowCount] int);
INSERT INTO #Cnt (ObjectName, [RowCount])
EXEC sp_msforeachtable N'SELECT ''?'' AS ObjectName, COUNT(*) AS [RowCount]
FROM ?;';
SELECT *
FROM #cnt;
DROP TABLE #cnt;
:
CURSOR
但是,如果我没记错的话,后一种方法实际上确实使用了{
"status":"true",
"select":[
{
"Type":"MARKET_WORKING",
"Question":"WHICH BRAND COUNTER IS IT?",
"option1":"USPA",
"option2":"HANES",
"option3":"USPA & HANES ",
"option4":""
}
],
"text":[
{
"Type":"MARKET_WORKING",
"Question":"WHAT IS THE STOCK QTY AVAILABLE OF INNERWEARS?",
"option1":"INNERWEARS TOP ",
"option2":"INNERWEARS BOTTOM ",
"option3":"",
"option4":""
},
{
"Type":"MARKET_WORKING",
"Question":"WHAT IS THE STOCK QTY AVAILABLE OF COMFORTWEAR?",
"option1":"COMFORT WEAR TOP",
"option2":"COMFORT WEAR BOTTOM",
"option3":"",
"option4":""
}
]
}
。
答案 1 :(得分:0)
您在这里查看了脚本。
IF OBJECT_ID('tempdb..#Dyn') IS NOT NULL
DROP TABLE #Dyn
SELECT Name, ROW_NUMBER() OVER (ORDER BY NEWID() ) AS SomeNumb
INTO #Dyn
FROM sys.tables
IF OBJECT_ID('tempdb..#ResultsTable') IS NOT NULL
DROP TABLE #ResultsTable
CREATE TABLE #ResultsTable (TotalRowCount INT)
DECLARE @Counter INT = 1
DECLARE @Sql NVARCHAR(MAX)
WHILE @Counter <= (SELECT COUNT(*) FROM #Dyn)
BEGIN
DECLARE @Table NVARCHAR(100) = (SELECT Name FROM #Dyn WHERE SomeNumb = @Counter)
SELECT @Sql = '
INSERT INTO #ResultsTable (TotalRowCount)
SELECT COUNT(*) AS Cnt
FROM #Dyn
WHERE Name = ''' + @Table + ''' AND SomeNumb = ' + CONVERT(NVARCHAR(10), @Counter)
EXECUTE (@Sql)
SET @Counter += 1
END
SELECT * FROM #ResultsTable
有些事情要提:
COUNT()
表中的#Dyn
将始终返回1,因为只有1条记录具有特定的表名。VARCHAR
)时,需要将所有非文字值都转换为NVARCHAR
或@Counter
。 编辑:如果您希望每个表的实际计数,则无需查询#Dyn
!
SELECT @Sql = '
INSERT INTO #ResultsTable (TotalRowCount)
SELECT COUNT(*) AS Cnt
FROM ' + QUOTENAME(@Table) +
EXECUTE (@Sql)