196

このクエリを実行しようとしています:

declare @tablename varchar(50)
set @tablename = 'test'
select * from @tablename

これにより、次のエラーが発生します。

メッセージ 1087、レベル 16、状態 1、行 5

テーブル変数「@tablename」を宣言する必要があります。

テーブル名を動的に設定する正しい方法は何ですか?

4

10 に答える 10

151

質問のような静的クエリの場合、テーブル名と列名は静的である必要があります。

動的クエリの場合、完全な SQL を動的に生成し、sp_executesql を使用して実行する必要があります。

異なるデータベースの同じテーブル間でデータを比較するために使用されるスクリプトの例を次に示します。

静的クエリ:

SELECT * FROM [DB_ONE].[dbo].[ACTY]
EXCEPT
SELECT * FROM [DB_TWO].[dbo].[ACTY]

tableとの名前を簡単に変更したいので、次のschema動的クエリを作成しました。

declare @schema varchar(50)
declare @table varchar(50)
declare @query nvarchar(500)

set @schema = 'dbo'
set @table = 'ACTY'

set @query = 'SELECT * FROM [DB_ONE].[' + @schema + '].[' + @table + '] EXCEPT SELECT * FROM [DB_TWO].[' + @schema + '].[' + @table + ']'

EXEC sp_executesql @query

動的クエリには考慮する必要のある多くの詳細があり、維持するのが難しいため、以下をお読みになることをお勧めします:動的 SQL の呪いと祝福

于 2010-05-15T01:14:49.247 に答える
115

最後のステートメントを次のように変更します。

EXEC('SELECT * FROM ' + @tablename)

これが私がストアドプロシージャでマイニングする方法です。最初のブロックは変数を宣言し、現在の年と月の名前(この場合はTEST_2012OCTOBER)に基づいてテーブル名を設定します。次に、データベースにすでに存在するかどうかを確認し、存在する場合は削除します。次に、次のブロックはSELECT INTOステートメントを使用してテーブルを作成し、別のテーブルのレコードにパラメーターを設定します。

--DECLARE TABLE NAME VARIABLE DYNAMICALLY
DECLARE @table_name varchar(max)
SET @table_name =
    (SELECT 'TEST_'
            + DATENAME(YEAR,GETDATE())
            + UPPER(DATENAME(MONTH,GETDATE())) )

--DROP THE TABLE IF IT ALREADY EXISTS
IF EXISTS(SELECT name
          FROM sysobjects
          WHERE name = @table_name AND xtype = 'U')

BEGIN
    EXEC('drop table ' +  @table_name)
END

--CREATES TABLE FROM DYNAMIC VARIABLE AND INSERTS ROWS FROM ANOTHER TABLE
EXEC('SELECT * INTO ' + @table_name + ' FROM dbo.MASTER WHERE STATUS_CD = ''A''')
于 2012-10-05T13:52:44.917 に答える
38

変数にテーブル名を使用することはできません。代わりにこれを行う必要があります:

DECLARE @sqlCommand varchar(1000)
SET @sqlCommand = 'SELECT * from yourtable'
EXEC (@sqlCommand)
于 2010-05-15T01:13:25.723 に答える
17

SQL コンテンツを動的に生成する必要があります。

declare @tablename varchar(50)

set @tablename = 'test'

declare @sql varchar(500)

set @sql = 'select * from ' + @tablename

exec (@sql)
于 2010-05-15T01:21:40.307 に答える
-1
Declare @fs_e int, @C_Tables CURSOR, @Table varchar(50)

SET @C_Tables = CURSOR FOR
        select name from sysobjects where OBJECTPROPERTY(id, N'IsUserTable') = 1 AND name like 'TR_%'
OPEN @C_Tables
FETCH @C_Tables INTO @Table
    SELECT @fs_e = sdec.fetch_Status FROM sys.dm_exec_cursors(0) as sdec where sdec.name = '@C_Tables'

WHILE ( @fs_e <> -1)
    BEGIN
        exec('Select * from ' + @Table)
        FETCH @C_Tables INTO @Table
        SELECT @fs_e = sdec.fetch_Status FROM sys.dm_exec_cursors(0) as sdec where sdec.name = '@C_Tables'
    END
于 2016-08-10T07:52:35.847 に答える