2011-11-07 8 views
25

Próbowałem wybrać ... do temp tabeli # TempTable w sp_Executedsql. Nie został pomyślnie wstawiony lub nie, ale istnieją tam komunikaty napisane (dotyczy 359 wierszy), które oznaczają pomyślne wstawienie? Script poniżejWykonaj sp_executeSql dla select ... na #table, ale nie można wybrać danych tabeli temp.

DECLARE @Sql NVARCHAR(MAX); 
SET @Sql = 'select distinct Coloum1,Coloum2 into #TempTable 
      from SPCTable with(nolock) 
      where Convert(varchar(10), Date_Tm, 120) Between @Date_From And @Date_To'; 

SET @Sql = 'DECLARE @Date_From VARCHAR(10); 
      DECLARE @Date_To VARCHAR(10); 
      SET @Date_From = '''+CONVERT(VARCHAR(10),DATEADD(d,DATEDIFF(d,0,GETDATE()),0)-1,120)+'''; 
      SET @Date_To = '''+CONVERT(VARCHAR(10),DATEADD(d,DATEDIFF(d,0,GETDATE()),0)-1,120)+'''; 
      '+ @Sql; 

EXECUTE sp_executesql @Sql; 

Po stracony, jego powrót na mnie wiadomości (359 row (s) affected). Następnie przy próbie wybrania danych z #TempTable.

Select * From #TempTable; 

jego powrotu do mnie:

Msg 208, Level 16, State 0, Line 2 
Invalid object name '#TempTable'. 

Podejrzewa się, że tylko jej tylko część roboczą 'Select'. Wkładka nie działa. jak to naprawić?

Odpowiedz

25

lokalne tabeli tymczasowej #table_name jest widoczny tylko w bieżącej sesji, globalne tabele tymczasowe ##table_name są widoczne we wszystkich sesjach. Oba życia do zakończenia sesji. sp_executesql - tworzy własną sesję (być może słowo "zakres" byłoby lepsze), dlatego tak się dzieje.

+2

myślę, że słowo „zakres” będzie lepiej. 'DECLARE @sql NVARCHAR (MAX); SET @sql = 'SELECT @@ SPID'; EXECUTE sp_executesql @sql; SELECT @@ SPID' –

+0

Dzięki @Michal, przypomniałem już tę metodę użycia. Jeszcze raz dziękuję – Worgon

+0

Pytanie brzmiało, jak to naprawić. Nie dlatego jego zerwanie. Podałem poprawną odpowiedź poniżej. 'INSERT INTO @tmpTbl EXEC sp_executesql @ sql' –

3

Tabele tymczasowe działają tylko tak długo, jak połączenie, które je tworzy. Spodziewam się, że nieumyślnie wydasz polecenie wyboru w osobnym połączeniu. Możesz to przetestować, natychmiast wprowadzając wstawkę do nieprywatnego stołu i sprawdzając, czy są tam twoje dane. W takim przypadku możesz wrócić do oryginalnego rozwiązania i pamiętaj, aby przekazać obiekt połączenia do swojego wyboru.

29

Użycie globalnej tabeli tymczasowej w tym scenariuszu może spowodować problemy, ponieważ tabela może występować między sesjami i może powodować problemy z asynchronicznym użyciem kodu wywołującego.

Lokalna tabela tymczasowa może być używana, jeśli zdefiniowano przed wywołaniem sp_executesql np.

CREATE TABLE #tempTable(id int); 

sp_executesql 'INSERT INTO #tempTable SELECT myId FROM myTable'; 

SELECT * FROM #tempTable; 
1

Aby obejść ten problem, użyj polecenia CREATE TABLE #TEMPTABLE najpierw wygenerować pustą temp tabeli przed uruchomieniem sp_executesql. Następnie uruchom INSERT INTO #TEMPTABLE za pomocą sp_executesql. To zadziała. W ten sposób przezwyciężyłem ten problem, ponieważ mam konfigurację, w której wszystkie moje zapytania są zwykle uruchamiane przez sp_executesql.

1
declare @sql varchar(1000) 
set @sql="select * into #t from table;" 
set @sql [email protected] + "select * from #t;" 

execute SP_EXECUTESQL @sql 
4

W swojej ciąg @sql, nie wkładaj into #TempTable. Zamiast tego zadzwoń na swoje oświadczenie SELECT bez oświadczenia INSERT.

Wreszcie, włóż wyniki do swojej tymczasowej tabeli tak:

INSERT INTO @tmpTbl EXEC sp_executesql @sql 
Powiązane problemy