我经常通过生成返回语句的查询来解决这个问题,然后将这些语句复制粘贴到一个新的查询窗口中并执行它们。我喜欢这种方法,因为我在执行语句之前看到了我的语句,并且还可以使用解析器快速识别它们的问题。考虑到这一点,这是我的查询:
SELECT DISTINCT ''
    + ' INSERT INTO ' + 'dbo.' + QUOTENAME(name)
    + ' (' + dbo.COLUMN_NAMES('dbo', name) + ')'
    + ' SELECT ' + dbo.COLUMN_NAMES('dbo', name)
    + ' FROM ' + 'db_owner.' + QUOTENAME(name)
FROM sys.tables
-- add your own WHERE clauses to only execute against specific tables
就是这么简单。这将返回一个 INSERT INTO ... SELECT FROM... 语句列表,我可以简单地将其复制粘贴到一个新的查询窗口中。
如果您想知道为什么不只使用 SELECT *,那仅仅是因为如果您的表有 ID 列,那么您将需要显式命名这些列并在前后添加 SET_IDENTITY 语句。
COLUMN_NAMES 函数是一个非常不言自明的函数,它返回指定表的逗号分隔列名:
CREATE FUNCTION COLUMN_NAMES
(
    @tableschema VARCHAR(MAX),
    @tablename VARCHAR(MAX)
)
RETURNS VARCHAR(MAX)
AS
BEGIN
RETURN (
    REPLACE(
        (SELECT QUOTENAME(COLUMN_NAME) AS 'data()'
         FROM INFORMATION_SCHEMA.COLUMNS
         WHERE TABLE_SCHEMA=@tableschema AND TABLE_NAME=@tablename ORDER BY ORDINAL_POSITION FOR XML PATH('')),
         ' ',', '))
END
GO