我在两个不同的数据库中有两个表。
我的第一个表是旧版本,列数少于第二个表。
我想将旧表的内容复制到新表中。
在每种数据库表中,在这种情况下有几种分布。
如何在不必为每个表手动编写列名的情况下快速将数据从旧表复制到新表?
谢谢!
答案 0 :(得分:1)
您可以“避免手动编写列名称"在SSMS中通过拖放"列"对象资源管理器中的表下的文件夹到查询窗口(只需将拖动的项目保持在空格或要显示名称的字符位置)。所有列名称将以逗号分隔显示。
您也可以尝试这样的方法来获取两个表之间通用的列列表(然后编写INSERT语句很简单)。
SELECT
Substring((
SELECT
', ' + S.COLUMN_NAME
FROM
INFORMATION_SCHEMA.COLUMNS S
INNER JOIN INFORMATION_SCHEMA.COLUMNS D
ON S.COLUMN_NAME = D.COLUMN_NAME
WHERE
S.TABLE_SCHEMA = 'dbo'
AND S.TABLE_NAME = 'Source Table'
AND D.TABLE_SCHEMA = 'dbo'
AND D.TABLE_NAME = 'Destination Table'
FOR XML PATH(''), TYPE
).value('.[1]', 'nvarchar(max)'), 3, 21474783647)
;
您还可以创建一个SSIS包,只需将所有数据从一个表移动到另一个表。匹配的列名将自动链接。根据您对SSIS的熟悉程度,这可能需要2分钟,或者可能需要2个小时。
答案 1 :(得分:0)
以下代码应该完成这项工作。 基本上它的作用是:
1。从两个表中收集列名称 2.将列名相交,以过滤掉仅存在于1个表中的列 3.获取一个字符串,该字符串是由逗号分隔的列名 4.使用阶段#3中的字符串创建插入命令 5.执行第4阶段的命令。
--BEGIN TRAN
DECLARE @oldName NVARCHAR(50) = 'OldTableName', @newName NVARCHAR(50) = 'newTableName'
DECLARE @oldDBName NVARCHAR(50) = '[OldDBName].[dbo].['+@oldName+']', @newDBName NVARCHAR(50) = '[newDBName].[dbo].['+@newName+']'
/*This table variable will have columns that exists in both table*/
DECLARE @tCommonColumns TABLE(
ColumnsName NVARCHAR(max) NOT NULL
);
INSERT INTO @tCommonColumns
SELECT column_name --,*
FROM information_schema.columns
WHERE table_name = @oldName
AND COLUMNPROPERTY(object_id(@oldName), column_name, 'IsIdentity') = 0 --this will make sure you ommit IDentity columns
INTERSECT
SELECT column_name --, *
FROM information_schema.columns
WHERE table_name = @newName
AND COLUMNPROPERTY(object_id(@newName), column_name,'IsIdentity') = 0--this will make sure you ommit IDentity columns
--SELECT * FROM @tCommonColumns
/*Get the columns as a comma seperated string */
DECLARE @columns NVARCHAR(max)
SELECT DISTINCT
@columns = STUFF((SELECT ', ' + cols.ColumnsName
FROM @tCommonColumns cols
FOR XML Path('')),1,1,'')
FROM @tCommonColumns
PRINT @columns
/*Create tyhe insert command*/
DECLARE @InserCmd NVARCHAR(max)
SET @InserCmd =
'INSERT INTO '+@newDBName +' ('+@columns +')
SELECT '+@columns +' FROM '+@oldDBName
PRINT @InserCmd
/*Execute the command*/
EXECUTE sp_executesql @InserCmd
--ROLLBACK
请注意,如果FOREIGN KEY Constraints已在旧表中实现但未在新表中实现,则此脚本可能会失败。
修改强>
该查询已更新为省略Identity
列。
编辑2:
更新了查询以支持表的不同数据库(请确保设置@oldName
,@newName
,@oldDBName
,@newDBName
变量以匹配实际凭据。
答案 2 :(得分:0)
全部谢谢!
我建议它更通用:)
--BEGIN TRAN
DECLARE @Tablename NVARCHAR(50)
SET @Tablename = 'tableName'
DECLARE @Schemaname NVARCHAR(50)
SET @Schemaname = 'schemaName'
DECLARE @Datasource NVARCHAR(50)
SET @Datasource = 'dataSource'
DECLARE @Datadest NVARCHAR(50)
SET @Datadest = 'dataDestination'
/*This table variable will have columns that exists in both table*/
DECLARE @tCommonColumns TABLE(
ColumnsName NVARCHAR(max) NOT NULL
);
--INSERT INTO @tCommonColumns
DECLARE @sql NVARCHAR(max)
SET @sql = 'SELECT column_name
FROM ' + @Datasource + '.information_schema.columns
WHERE table_name = ''' + @Tablename + '''
AND COLUMNPROPERTY(object_id(''' + @Datasource + '.' + @Schemaname + '.' + @Tablename + '''), column_name, ''IsIdentity'') = 0' --this will make sure you ommit IDentity columns
SET @sql = @sql + ' INTERSECT
SELECT column_name
FROM ' + @Datadest + '.information_schema.columns
WHERE table_name = ''' + @Tablename + '''
AND COLUMNPROPERTY(object_id(''' + @Datadest + '.' + @Schemaname + '.' + @Tablename + '''), column_name, ''IsIdentity'') = 0' --this will make sure you ommit IDentity columns'
INSERT INTO @tCommonColumns EXECUTE sp_executesql @sql
-- SELECT * FROM @tCommonColumns
/*Get the columns as a comma seperated string */
DECLARE @columns NVARCHAR(max)
SELECT DISTINCT
@columns = STUFF((SELECT ', ' + cols.ColumnsName
FROM @tCommonColumns cols
FOR XML Path('')),1,1,'')
FROM @tCommonColumns
--PRINT @columns
/*Create tyhe insert command*/
DECLARE @InserCmd NVARCHAR(max)
SET @InserCmd =
'INSERT INTO '+@Datadest+'.'+@Schemaname+'.'+@Tablename +' ('+@columns +')
SELECT '+@columns +' FROM '+@Datasource+'.'+@Schemaname+'.'+@Tablename
PRINT @InserCmd
/*Execute the command*/
--EXECUTE sp_executesql @InserCmd
--ROLLBACK
答案 3 :(得分:-2)
这样的事情:
Insert into dbo.Newtbl
SELECT * FROM dbo.OldTbl