Erklären müssen die Skalare variable
Schrieb ich das SQL in einer gespeicherten Prozedur aber nicht funktioniert,
declare @tableName varchar(max) = 'TblTest'
declare @col1Name varchar(max) = 'VALUE1'
declare @col2Name varchar(max) = 'VALUE2'
declare @value1 varchar(max)
declare @value2 varchar(200)
execute('Select TOP 1 @value1='+@col1Name+', @value2='+@col2Name+' From '+ @tableName +' Where ID = 61')
select @value1
execute('Select TOP 1 @value1=VALUE1, @value2=VALUE2 From TblTest Where ID = 61')
Diese SQL-wirft diesen Fehler:
Erklären muß, die Skalare variable "@Wert1".
Ich bin die Generierung der SQL dynamisch und ich will den Wert in eine variable. Was soll ich tun?
- Warum verwenden Sie dynamische Abfragen ? Ich sehe keinen Grund für die Verwendung von dynamischen Abfragen für Ihre Frage.
- Ich weiß nicht, Tabellenname und Spaltenname.Also ich bin erstellen einer Abfrage dynamisch.
- Also alle diese Quell-Tabellen haben mindestens drei Spalten:
VALUE1
,VALUE2
undID
? Auch diese Spalten haben die gleichen Datentypen ? Auch die Zahl der in diesen Tabellen ist variabel oder konstant ? - Ja, Alle dieser Spalten-Typ ist varchar. Es ist nicht nötig, um die Konvertierung oder casting.
- Nicht dumm nach unten in Frage, weil Sie denken, es wird es einfacher machen. Wenn die Tabellen-und Spaltennamen dynamisch sind, umfassen, dass ein Teil des Codes zu.
- Außerdem, warum müssen Sie TOP-1? Glauben Sie wirklich, haben Sie mehrere Zeilen mit ID = 61? Wenn dem so ist, dann macht Sie zwei Gründe, warum das ist eine schreckliche und irreführend Spalte name.
- Dies ist Beispiel-Abfrage, Bitte glaube nicht, dass dieses Thema
Du musst angemeldet sein, um einen Kommentar abzugeben.
Dem Grund, dass Sie immer die
DECLARE
Fehler von Ihrer dynamischen Aussage ist, da dynamische Anweisungen verarbeitet werden, in separaten Chargen, die hinausläuft auf eine Frage des Umfangs. Zwar gibt es eine mehr formale definition der Bereiche in SQL Server verfügbar, die ich gefunden habe, es genügt in der Regel halten die folgenden drei im Auge, geordnet von der höchsten Verfügbarkeit zu niedrigsten Verfügbarkeit:Globalen:
Objekte, die verfügbar sind server-weiten, wie temporäre Tabellen erstellt, mit einer doppelten Rautenzeichen (
##GLOBALTABLE
aber Sie mag, um den Anruf # ). Seien Sie sehr vorsichtig Globale Objekte, wie Sie mit jeder Anwendung, die SQL Server-oder anders; diese Art von Dingen sind in der Regel am besten vermieden werden. Was ich im wesentlichen sagen, ist, dass dieser Bereich im Verstand, die speziell als Erinnerung zu bleiben, aus ihm heraus.Sitzung:
Objekte, die Referenz gesperrt werden, um eine bestimmte spid. Aus der Spitze von meinem Kopf, die einzige Art von session-Objekt, das ich denken kann ist eine normale temporäre Tabelle, die definiert, wie #Tabelle. Wird im session-scope bedeutet im wesentlichen, dass, nachdem der Stapel ( gekündigt durch
GO
) abgeschlossen ist, Verweise auf dieses Objekt wird weiterhin erfolgreich beheben. Diese technisch zugänglich durch andere Sitzungen, aber es wäre schon ein Kunststück tun, um so programmatisch, wie Sie Art von randomisierten Namen in tempdb und der Zugriff auf Sie ist ein bisschen wie ein Schmerz in den Arsch sowieso.Öffnen einer neuen session ( eine Verbindung mit einer separaten spid ), der zweite batch oben scheitern würde, wie die Sitzung wäre nicht in der Lage zu lösen, die
#t_Test
Objekt name.Batch:
Normale Variablen, wie Ihr
@value1
und@value2
, beschränkt nur für die Batchdatei, in der Sie deklariert sind. Im Gegensatz zu#Temp
Tabellen, sobald Sie Ihre query-block schlägt in eineGO
, diese Variablen nicht verfügbar, bis die session. Dies ist der Umfang, die Erstellung Ihrer Fehler.Okay, so what?
Was passiert hier mit Ihrer dynamischen Aussage ist, dass die
EXECUTE()
Befehl effektiv bewertet als separater batch, ohne die batch-Ausführung aus.EXECUTE()
ist gut und alle, aber seit der Einführungsp_executesql()
habe, verwende ich ersteres nur in den einfachsten Fällen ( explizit, wenn es gibt sehr wenig "dynamische" element der meine Aussagen überhaupt, in Erster Linie ein "trick" ansonsten unverbindlich-DDL -CREATE
Aussagen zu laufen, in der Mitte der anderen Chargen ). @AaronBertrand ist Antwort oben ist ähnlich und wird ähnlich in der Leistung zu den nachfolgenden, durch die Nutzung der Funktion des Optimierers bei der Auswertung dynamische Anweisungen, aber ich dachte, es könnte sinnvoll sein, zu erweitern auf die@param
gut, parameter.Sollten Sie auch an Ihre Eingabe, wie, wo 61 kommt, da der richtige Parameter (aber Sie werden nicht in der Lage, übergeben von Tabellen-und Spaltennamen, die Art und Weise).
sp_executesql
aufrufen und ausführen direktDeclare @v1 varchar(max), @v2 varchar(200); SELECT @v1 = value1, @v2 = value2 FROM dbo.TblTest WHERE ID = 61;
?Hier ist ein einfaches Beispiel :
Unten ausführen von Anweisungen in einem einzigen batch (durch Auswahl von alle)
Als ich versuchte, zum ausführen von Anweisungen 1,2,3 einzeln, ich hatte den gleichen Fehler.
Aber auch ausgeführt, wenn Sie alle auf einmal, es funktionierte.
Der Grund ist, dass SQL ausführt erklären, exec-Anweisungen in verschiedenen Sitzungen.
Offen für weitere Korrekturen.
Diese wird in SQL Server auftreten, wenn Sie laufen Sie nicht alle Aussagen auf einmal. Wenn Sie die Hervorhebung einer Reihe von Aussagen und ausführen der folgenden:
Und dann versuchen Sie, einen anderen Satz von Aussagen wie:
Erhalten Sie diese Fehlermeldung.