58

あるデータベースから別のデータベースにデータをインポートして変換するためのストアド プロシージャを作成しました。各インポートは単一の会社 ID を取り、この会社に関連するすべてのデータをインポートします。

変換ステップを支援するために、一時テーブルを使用します。スクリプト レビューの一環として、一時テーブルではなくテーブル変数を使用するように言われました。レビュアーは、2 つの異なるインポートを同時に実行すると、一時テーブルが共有され、インポートが破損すると主張しています。


質問:

  • 2 つの異なるインポートを同時に実行すると、一時テーブルが共有されるというのは本当ですか?
  • 各呼び出しEXECは新しいスコープを作成しますか?

これはスクリプトの不自然な例です。

CREATE PROC [dbo].[ImportCompany]
(
    @CompanyId AS INTEGER
)
AS
EXEC [dbo].[ImportAddress] @CompanyId = @CompanyId 
--Import other data

CREATE PROC [dbo].[ImportAddress]
(
    @CompanyId AS INTEGER
)
AS
    CREATE TABLE #Companies (OldAddress NVARCHAR(128), NewAddress NVARCHAR(128))
    INSERT INTO #Companies(OldAddress, NewAddress)
    SELECT
        Address as OldAddress,
        'Transformed ' + Address as NewAddress
    FROM
        [OldDb].[dbo].[Addresses]
    WHERE
        CompanyId = @CompanyId

    --Do stuff with the transformed data

    DROP TABLE #Companies

EXEC [dbo].[ImportCompany] @CompanyId = 12345
4

4 に答える 4

74

からCREATE TABLE:

ローカル一時テーブルは現在のセッションでのみ表示されます

そして更に重要なことに):

複数のユーザーが同時に実行できるストアド プロシージャまたはアプリケーションでローカル一時テーブルが作成された場合、データベース エンジンは、異なるユーザーによって作成されたテーブルを区別できる必要があります[原文のまま - ほとんどの場合、これはセッションではないと言うべきですユーザー] . データベース エンジンDatabase Engine は、数値のサフィックスを各ローカル一時テーブル名に内部的に追加することによってこれを行います。

これは、共有されると言った人の主張に正確に反論します。


また、手順の最後に必要はありませんDROP TABLE(同じリンクから):

ストアド プロシージャで作成されたローカル一時テーブルは、ストアド プロシージャの終了時に自動的に削除されます。

于 2013-09-04T12:56:01.373 に答える