EXEC sp_rename 在 while 循环中执行几次后停止
EXEC sp_rename stop after several times in a while loop
我尝试用 table 的第一行重命名我的列名。
(我知道,它在 SQL 中没有意义 'a first row without order by',但我必须为我的测试这样做)。
所以,我不想动态搜索我的旧列名和新列名以在 while 循环中执行 sp_rename 。
这是ma代码:
DECLARE @i INT;
SET @i = 0;
DECLARE @oldnom NVARCHAR(MAX);
DECLARE @newnom NVARCHAR(MAX)
DECLARE @sSQL NVARCHAR(MAX);
DECLARE @ParmDefinition NVARCHAR(MAX);
DECLARE @tablename NVARCHAR(MAX) ;
SET @tablename = N'Produit_A';
WHILE @i < (SELECT MAX(rownum) FROM (SELECT ROW_NUMBER() OVER(ORDER BY ORDINAL_POSITION ASC) AS rownum,COLUMN_NAME FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_NAME = @tablename AND COLUMN_NAME like 'Prop%') truc)
BEGIN
SET @oldnom = 'Prop_'+CAST(@i AS NVARCHAR(MAX))
SET @oldnom = 'dbo.'+@tablename+'.['+@oldnom+']'
SET @i = @i + 1
SELECT @sSQL = N'SELECT TOP 1 @retvalOUT = COALESCE('+@oldnom+','''+@oldnom+''') FROM dbo.' + @tablename;
SET @ParmDefinition = N'@retvalOUT NVARCHAR(MAX) OUTPUT';
EXEC sp_executesql @sSQL, @ParmDefinition, @retvalOUT=@newnom OUTPUT;
IF @newnom <> @oldnom
BEGIN
SELECT @oldnom, @newnom;
-- EXEC sp_rename @oldnom, @newnom;
END
END
我的请求工作正常,SELECT @oldnom,@newnom; return 所有需要重命名的列,并且可以使我的 sp_rename.
然而,当我取消注释 EXEC sp_rename @oldnom, @newnom;并执行我的请求。
我的专栏重命名很好,但不是全部。我的 exec 在一定数量后无错误地停止。
如果我改变了 while 的开始,以下列也被很好地重命名,所以问题不是由于某个列的错误。
我不明白为什么 select 工作正常但 exec sp_rename 几次后停止工作...
我考虑过单个请求的执行限制,但找不到任何相关信息。
我还考虑了 return 由 sp_rename
命令编辑的错误消息(注意:更改对象名称的任何部分可能会破坏脚本和存储过程。),但同样,没有信息.
您没有向我们提供第一行的列名,所以我们不得不失明。
但基于它在您不重命名时有效的事实,我敢打赌问题出在您的查询中:
@i < select max(rownum) from (.....)truc
请注意,此查询在每 次迭代后计算。当您不重命名列时效果很好,因为每次 returns 都是一样的。
但是如果您确实重命名了列,您将从此查询中删除行,因为:
AND COLUMN_NAME like 'Prop%'
这会导致您的查询每隔一列“跳转”一次。示例:
第一次迭代,row_number=1,列重命名为 [SomeColumn1Title]。
第二次迭代。第一行不再是 [SomeColumn1Title],而是 [SomeColumn2Title]。然而,你在@i=2,所以会发生的是第 3 列将被重命名。等等。
这段代码真的很不稳定。只需使用游标,它只会对您的查询求值一次。
问题出在我的 while 循环条件中。
我将修复我的代码并使用游标来避免循环。
非常感谢 !
这是我更正的代码:
DECLARE @tablename NVARCHAR(MAX);
DECLARE
@oldnom NVARCHAR(MAX),
@newnom NVARCHAR(MAX),
@sSQL NVARCHAR(MAX),
@ParmDefinition NVARCHAR(MAX),
@requete NVARCHAR(MAX);
SET @tablename = N'Produit_A';
SET @requete = N'';
DECLARE cursor_col CURSOR FOR
SELECT name
FROM sys.columns
WHERE object_id = OBJECT_ID('bdd_canon.['+@tablename+']');
OPEN cursor_col;
FETCH NEXT FROM cursor_col INTO @oldnom ;
WHILE @@FETCH_STATUS = 0
BEGIN
SELECT @sSQL = N'SELECT TOP 1 @retvalOUT = COALESCE('+@oldnom+','''+@oldnom+''') FROM bdd_canon.' + @tablename;
SET @ParmDefinition = N'@retvalOUT NVARCHAR(MAX) OUTPUT';
EXEC sp_executesql @sSQL, @ParmDefinition, @retvalOUT=@newnom OUTPUT;
IF @newnom <> @oldnom
BEGIN
SET @oldnom = '''bdd_canon.'+@tablename+'.['+@oldnom+']'''
SET @newnom = ''''+@newnom+''''
SET @requete = @requete + 'EXEC sp_rename '+@oldnom+', '+@newnom+',''COLUMN''; ';
END
FETCH NEXT FROM cursor_col INTO @oldnom ;
END;
EXEC sp_executesql @requete
CLOSE cursor_col;
DEALLOCATE cursor_col;
我尝试用 table 的第一行重命名我的列名。 (我知道,它在 SQL 中没有意义 'a first row without order by',但我必须为我的测试这样做)。 所以,我不想动态搜索我的旧列名和新列名以在 while 循环中执行 sp_rename 。 这是ma代码:
DECLARE @i INT;
SET @i = 0;
DECLARE @oldnom NVARCHAR(MAX);
DECLARE @newnom NVARCHAR(MAX)
DECLARE @sSQL NVARCHAR(MAX);
DECLARE @ParmDefinition NVARCHAR(MAX);
DECLARE @tablename NVARCHAR(MAX) ;
SET @tablename = N'Produit_A';
WHILE @i < (SELECT MAX(rownum) FROM (SELECT ROW_NUMBER() OVER(ORDER BY ORDINAL_POSITION ASC) AS rownum,COLUMN_NAME FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_NAME = @tablename AND COLUMN_NAME like 'Prop%') truc)
BEGIN
SET @oldnom = 'Prop_'+CAST(@i AS NVARCHAR(MAX))
SET @oldnom = 'dbo.'+@tablename+'.['+@oldnom+']'
SET @i = @i + 1
SELECT @sSQL = N'SELECT TOP 1 @retvalOUT = COALESCE('+@oldnom+','''+@oldnom+''') FROM dbo.' + @tablename;
SET @ParmDefinition = N'@retvalOUT NVARCHAR(MAX) OUTPUT';
EXEC sp_executesql @sSQL, @ParmDefinition, @retvalOUT=@newnom OUTPUT;
IF @newnom <> @oldnom
BEGIN
SELECT @oldnom, @newnom;
-- EXEC sp_rename @oldnom, @newnom;
END
END
我的请求工作正常,SELECT @oldnom,@newnom; return 所有需要重命名的列,并且可以使我的 sp_rename.
然而,当我取消注释 EXEC sp_rename @oldnom, @newnom;并执行我的请求。
我的专栏重命名很好,但不是全部。我的 exec 在一定数量后无错误地停止。
如果我改变了 while 的开始,以下列也被很好地重命名,所以问题不是由于某个列的错误。
我不明白为什么 select 工作正常但 exec sp_rename 几次后停止工作...
我考虑过单个请求的执行限制,但找不到任何相关信息。
我还考虑了 return 由 sp_rename
命令编辑的错误消息(注意:更改对象名称的任何部分可能会破坏脚本和存储过程。),但同样,没有信息.
您没有向我们提供第一行的列名,所以我们不得不失明。
但基于它在您不重命名时有效的事实,我敢打赌问题出在您的查询中:
@i < select max(rownum) from (.....)truc
请注意,此查询在每 次迭代后计算。当您不重命名列时效果很好,因为每次 returns 都是一样的。
但是如果您确实重命名了列,您将从此查询中删除行,因为:
AND COLUMN_NAME like 'Prop%'
这会导致您的查询每隔一列“跳转”一次。示例:
第一次迭代,row_number=1,列重命名为 [SomeColumn1Title]。
第二次迭代。第一行不再是 [SomeColumn1Title],而是 [SomeColumn2Title]。然而,你在@i=2,所以会发生的是第 3 列将被重命名。等等。
这段代码真的很不稳定。只需使用游标,它只会对您的查询求值一次。
问题出在我的 while 循环条件中。 我将修复我的代码并使用游标来避免循环。 非常感谢 ! 这是我更正的代码:
DECLARE @tablename NVARCHAR(MAX);
DECLARE
@oldnom NVARCHAR(MAX),
@newnom NVARCHAR(MAX),
@sSQL NVARCHAR(MAX),
@ParmDefinition NVARCHAR(MAX),
@requete NVARCHAR(MAX);
SET @tablename = N'Produit_A';
SET @requete = N'';
DECLARE cursor_col CURSOR FOR
SELECT name
FROM sys.columns
WHERE object_id = OBJECT_ID('bdd_canon.['+@tablename+']');
OPEN cursor_col;
FETCH NEXT FROM cursor_col INTO @oldnom ;
WHILE @@FETCH_STATUS = 0
BEGIN
SELECT @sSQL = N'SELECT TOP 1 @retvalOUT = COALESCE('+@oldnom+','''+@oldnom+''') FROM bdd_canon.' + @tablename;
SET @ParmDefinition = N'@retvalOUT NVARCHAR(MAX) OUTPUT';
EXEC sp_executesql @sSQL, @ParmDefinition, @retvalOUT=@newnom OUTPUT;
IF @newnom <> @oldnom
BEGIN
SET @oldnom = '''bdd_canon.'+@tablename+'.['+@oldnom+']'''
SET @newnom = ''''+@newnom+''''
SET @requete = @requete + 'EXEC sp_rename '+@oldnom+', '+@newnom+',''COLUMN''; ';
END
FETCH NEXT FROM cursor_col INTO @oldnom ;
END;
EXEC sp_executesql @requete
CLOSE cursor_col;
DEALLOCATE cursor_col;