1826 Stimmen

Einfügen in ... Werte ( SELECT ... FROM ... )

Ich versuche, die INSERT INTO einer Tabelle unter Verwendung der Eingabe einer anderen Tabelle. Obwohl dies für viele Datenbank-Engines durchaus machbar ist, scheine ich mich immer an die korrekte Syntax für die SQL Motor des Tages ( MySQL , Oracle , SQL-Server , Informix y DB2 ).

Gibt es eine Patentrezept-Syntax, die aus einem SQL-Standard stammt (z. B., SQL-92 ), die es mir ermöglichen würde, die Werte einzufügen, ohne mich um die zugrunde liegende Datenbank zu kümmern?

2 Stimmen

Dieses Beispiel funktioniert: insert into tag_zone select @tag,zoneid,GETDATE(),@positiong.STIntersects(polygon) from zone

2012voto

Claude Houle Punkte 38165

Versuchen Sie es:

INSERT INTO table1 ( column1 )
SELECT  col1
FROM    table2  

Dies ist ANSI-SQL-Standard und sollte mit jedem DBMS funktionieren.

Es funktioniert definitiv für:

  • Oracle
  • MS SQL Server
  • MySQL
  • Postgres
  • SQLite v3
  • Teradata
  • DB2
  • Sybase
  • Vertica
  • HSQLDB
  • H2
  • AWS RedShift
  • SAP HANA
  • Google Spanner

0 Stimmen

Wie kann man das umsetzen? "insert into Content as c (ContentP) select title from title as t wehre c.pageno = t.pageno" . DANKE

0 Stimmen

Ich bezweifle stark, dass alle von ihnen es sofort unterstützen - nur SQLite hat eine Mindestversion, aber es wäre auch für andere interessant, insbesondere für ORACLE.

0 Stimmen

@MindRoasterMir Das können Sie nicht tun. Wenn Sie eine Einfügung vornehmen, erstellen Sie eine neue Zeile in der Tabelle, so dass Sie keine vorhandene Zeile haben, mit der Sie vergleichen können (c.pageno = t.pageno). Sie suchen wahrscheinlich nach einem UPDATE oder MERGE (MS Sql)

1231voto

travis Punkte 34588

Die Antwort von Claude Houle : sollte gut funktionieren, und Sie können auch mehrere Spalten und andere Daten als gut:

INSERT INTO table1 ( column1, column2, someInt, someVarChar )
SELECT  table2.column1, table2.column2, 8, 'some string etc.'
FROM    table2
WHERE   table2.ID = 7;

Ich habe diese Syntax nur mit Access, SQL 2000/2005/Express, MySQL und PostgreSQL verwendet, so dass diese abgedeckt sein sollten. Sie sollte auch mit SQLite3 funktionieren.

1 Stimmen

Was wäre, wenn die Where-Bedingung in table2.country geändert wird und eine Anzahl von Zeilen größer als eins zurückgibt? Ich habe hier ein ähnliches Problem: stackoverflow.com/questions/36030370/

1 Stimmen

Es sollte kein Problem sein, mehr als eine Zeile einzufügen.

0 Stimmen

Ist es notwendig, dass wir in alle Spalten der Tabelle einfügen

230voto

kylieCatt Punkte 9924

Um nur einen Wert in einem Multiwert zu erhalten INSERT aus einer anderen Tabelle habe ich in SQLite3 folgendes gemacht:

INSERT INTO column_1 ( val_1, val_from_other_table ) 
VALUES('val_1', (SELECT  val_2 FROM table_2 WHERE val_2 = something))

4 Stimmen

Nur zur Klarstellung: Dies ist für SQLite3 nicht korrekt. Gemäß die Dokumentation die Quelldaten für die INSERT es entweder VALUES oder eine SELECT Aussage, nicht beides.

2 Stimmen

In der Dokumentation ist sie zwar nicht aufgeführt, aber sie funktioniert. Unabhängig davon denke ich, dass die Verwendung der select-Anweisung anstelle von Werten die Lesbarkeit verbessert.

2 Stimmen

Es funktioniert, wenn man einen Wert innerhalb einer Zeile angibt, aber für den allgemeineren Fall muss man viele Zeilen abrufen.

75voto

Jonathan Leffler Punkte 694013

Beide Antworten, die ich sehe, funktionieren speziell in Informix gut und sind im Grunde genommen Standard-SQL. Das heißt, die Notation:

INSERT INTO target_table[(<column-list>)] SELECT ... FROM ...;

funktioniert problemlos mit Informix und, wie ich annehme, mit allen DBMS. (Früher, vor 5 oder mehr Jahren, hat MySQL diese Art von Dingen nicht immer unterstützt; jetzt hat es eine anständige Unterstützung für diese Art von Standard-SQL-Syntax und, AFAIK, würde es mit dieser Notation gut funktionieren). Die Spaltenliste ist optional, gibt aber die Zielspalten in der Reihenfolge an, so dass die erste Spalte des Ergebnisses des SELECT in die erste aufgelistete Spalte geht, usw. Fehlt die Spaltenliste, geht die erste Spalte des Ergebnisses des SELECT in die erste Spalte der Zieltabelle.

Was sich von System zu System unterscheiden kann, ist die Notation, die zur Identifizierung von Tabellen in verschiedenen Datenbanken verwendet wird - der Standard sagt nichts über datenbankübergreifende (geschweige denn DBMS-übergreifende) Operationen aus. Bei Informix können Sie die folgende Notation verwenden, um eine Tabelle zu identifizieren:

[dbase[@server]:][owner.]table

Das heißt, Sie können eine Datenbank angeben, optional den Server, der diese Datenbank beherbergt, wenn sie sich nicht auf dem aktuellen Server befindet, gefolgt von einem optionalen Eigentümer, einem Punkt und schließlich dem eigentlichen Tabellennamen. Der SQL-Standard verwendet den Begriff Schema für das, was Informix als Eigentümer bezeichnet. In Informix kann also jede der folgenden Schreibweisen eine Tabelle bezeichnen:

table
"owner".table
dbase:table
dbase:owner.table
dbase@server:table
dbase@server:owner.table

Der Eigentümer muss im Allgemeinen nicht in Anführungszeichen gesetzt werden; wenn Sie jedoch Anführungszeichen verwenden, müssen Sie den Namen des Eigentümers richtig schreiben - es wird zwischen Groß- und Kleinschreibung unterschieden. Das heißt:

someone.table
"someone".table
SOMEONE.table

identifizieren alle dieselbe Tabelle. Bei Informix gibt es eine kleine Komplikation mit MODE-ANSI-Datenbanken, bei denen Besitzernamen im Allgemeinen in Großbuchstaben umgewandelt werden (informix ist die Ausnahme). Das heißt, in einer MODE ANSI-Datenbank (die nicht häufig verwendet wird) könnten Sie schreiben:

CREATE TABLE someone.table ( ... )

und der Name des Eigentümers im Systemkatalog würde "SOMEONE" lauten und nicht "someone". Wenn Sie den Namen des Eigentümers in doppelte Anführungszeichen setzen, wirkt er wie ein Bezeichner mit Trennzeichen. Bei Standard-SQL können begrenzte Bezeichner an vielen Stellen verwendet werden. In Informix können Sie sie nur im Zusammenhang mit Besitzernamen verwenden. In anderen Kontexten behandelt Informix sowohl Strings in einfachen als auch in doppelten Anführungszeichen als Strings, anstatt Strings in einfachen Anführungszeichen als Strings und Strings in doppelten Anführungszeichen als abgegrenzte Bezeichner zu trennen. (Der Vollständigkeit halber sei erwähnt, dass es eine Umgebungsvariable DELIMIDENT gibt, die auf einen beliebigen Wert gesetzt werden kann, wobei Y am sichersten ist, um anzugeben, dass doppelte Anführungszeichen immer begrenzte Bezeichner und einfache Anführungszeichen immer Zeichenketten umgeben).

Beachten Sie, dass MS SQL Server in eckigen Klammern eingeschlossene [begrenzte Bezeichner] verwenden kann. Das sieht für mich seltsam aus und ist sicherlich nicht Teil des SQL-Standards.

49voto

Weslor Punkte 21722

Um der ersten Antwort etwas hinzuzufügen, wenn wir nur wenige Datensätze aus einer anderen Tabelle benötigen (in diesem Beispiel nur einen):

INSERT INTO TABLE1
(COLUMN1, COLUMN2, COLUMN3, COLUMN4) 
VALUES (value1, value2, 
(SELECT COLUMN_TABLE2 
FROM TABLE2
WHERE COLUMN_TABLE2 like "blabla"),
value4);

8 Stimmen

Dieser Ansatz gilt nur für solche Unterabfragen, bei denen nur eine Spalte ausgewählt wird. Im Falle einer Unterabfrage mit mehreren Spalten wird der Fehler "Unterabfrage muss nur eine Spalte zurückgeben" ausgelöst. Übernehmen Sie dann die Antwort von @travis.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X