… Değerlerine ekle (SELECT… FROM…)


1427

Başka INSERT INTObir tablodan giriş kullanarak bir tabloya çalışıyorum . Bu, birçok veritabanı motoru için tamamen mümkün olsa da, her zaman SQLgünün motoru için doğru sözdizimini ( MySQL , Oracle , SQL Server , Informix ve DB2 ) hatırlamakta zorlanıyorum .

Temel veritabanı hakkında endişelenmeden değerleri eklememe izin veren bir SQL standardından (örneğin, SQL-92 ) gelen gümüş mermi sözdizimi var mı ?


1
bu örnek işe yarar: bölgeden tag_zone select @ tag, zoneid, GETDATE (), @ positiong.STIntersects (çokgen) içine ekler
Uğur Gümüşhan

Yanıtlar:


1611

Deneyin:

INSERT INTO table1 ( column1 )
SELECT  col1
FROM    table2  

Bu standart ANSI SQL'dir ve herhangi bir DBMS üzerinde çalışmalıdır

Kesinlikle çalışır:

  • torpil
  • MS SQL Sunucusu
  • MySQL
  • postgres
  • SQLite v3
  • Teradata
  • DB2
  • Sybase
  • Vertica
  • HSQLDB
  • H2
  • AWS RedShift
  • SAP HANA

947

Claude Houle'un cevabı : iyi çalışmalı ve ayrıca birden fazla sütun ve diğer verileriniz de olabilir:

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

Bu sözdizimini yalnızca Access, SQL 2000/2005 / Express, MySQL ve PostgreSQL ile kullandım, bu yüzden bunlar ele alınmalıdır. SQLite3 ile de çalışmalıdır.


1
Peki, nerede koşulu table2.country olarak değiştirilirse ve birden fazla satır sayısını döndürürse Burada benzer bir sorun var: stackoverflow.com/questions/36030370/…
vijayrana

1
Birden fazla satır eklemeyle ilgili bir sorun olmamalıdır.
rinukkusu

tablonun tüm sütunlarına
eklememiz

1
@maheshmnj hayır, yalnızca NOT NULL olarak ayarlanmış sütunların ve varsayılan değerin dahil edilmesi gerekmez, diğer sütunlar varsayılan değerlerine veya NULL olarak ayarlanır
travis

bilgi için teşekkürler
maheshmnj

148

INSERTBaşka bir tablodan çoklu bir değerde yalnızca bir değer elde etmek için SQLite3'te aşağıdakileri yaptım:

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

4
Sadece açıklama için: bu SQLite3 için yanlıştır. Gereğince belgeleri için kaynak veri INSERTolduğu ya VALUES ya da SELECTdeyim, ikisini birden değil.

2
Belgelerin listelemediği doğrudur, ancak çalışır. Ne olursa olsun, ben değerleri yerine select deyimi kullanarak daha okunabilir hale düşünüyorum.
Banjocat

1
Bir satır içindeki bir değeri belirtmek için çalışır, ancak daha genel durum çok sayıda satır almayı gerektirir.
Luchostein

Val_1 satırlar arasında değişmezse, SQLite3'te aşağıdaki sözdizimi işe yarayabilir mi? some_table'dan 'foo', some_column seçin - SQLServer 2014'te çalışır
Chris B

Belgeler bunu listeliyor (şimdi?): Bu sözdizimi INSERT INTO ... VALUES ([expr], [expr], ...)ve yollardan [expr]biri {{NOT} EXISTS} ([select-stmt])- select deyimi etrafındaki parantezin gerekli olduğunu unutmayın ( {}isteğe bağlı)
zapl

64

Gördüğüm her iki yanıt da Informix'te gayet iyi çalışıyor ve temelde standart SQL. Yani gösterim:

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

Informix ile iyi çalışır ve tüm DBMS beklenir. (5 veya daha fazla yıl önce, bu MySQL'in her zaman desteklemediği bir şeydir; şimdi bu tür standart SQL sözdizimi için iyi bir desteğe sahiptir ve AFAIK, bu gösterimde TAMAM çalışacaktır.) Sütun listesi isteğe bağlıdır, ancak hedef sütunları sırayla gösterir, bu nedenle SELECT sonucunun ilk sütunu listelenen ilk sütuna vb. girer. Sütun listesinin yokluğunda SELECT sonucunun ilk sütunu, hedef tablonun ilk sütunu.

Sistemler arasında farklı olan, farklı veritabanlarındaki tabloları tanımlamak için kullanılan gösterimdir - standardın veritabanları arası (DBMS bağımsız olarak) işlemler hakkında söyleyecek bir şeyi yoktur. Informix ile tablo tanımlamak için aşağıdaki gösterimi kullanabilirsiniz:

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

Yani, isteğe bağlı olarak geçerli sunucuda değilse o veritabanını barındıran sunucuyu tanımlayan bir veritabanı belirtebilirsiniz, ardından isteğe bağlı bir sahip, nokta ve son olarak gerçek tablo adı gelir. SQL standardı, Informix'in sahibi olarak adlandırdığı şema terimini kullanır. Böylece, Informix'te, aşağıdaki gösterimlerden herhangi biri bir tablo belirleyebilir:

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

Genel olarak sahibin kote edilmesine gerek yoktur; ancak, tırnak işaretleri kullanırsanız, sahip adının doğru yazılmasını sağlamanız gerekir. Büyük / küçük harf duyarlıdır. Yani:

someone.table
"someone".table
SOMEONE.table

hepsi aynı tabloyu tanımlar. Informix ile, sahip adlarının genellikle büyük harfe dönüştürüldüğü MODE ANSI veritabanlarında hafif bir komplikasyon vardır (informix istisnadır). Yani, bir MODE ANSI veritabanında (yaygın olarak kullanılmaz) şunları yazabilirsiniz:

CREATE TABLE someone.table ( ... )

ve sistem kataloğundaki sahip adı "birisi" yerine "SOMEONE" olur. Sahip adını çift tırnak içine alırsanız, sınırlandırılmış bir tanımlayıcı gibi davranır. Standart SQL ile, sınırlandırılmış tanımlayıcılar birçok yerde kullanılabilir. Informix ile bunları yalnızca sahip adlarında kullanabilirsiniz - diğer bağlamlarda Informix, tek tırnaklı dizeleri dize olarak ayırmak yerine çift tırnaklı dizeleri ayrılmış tanımlayıcılar olarak ayırmak yerine, hem tek tırnaklı hem de çift tırnaklı dizeleri dizeler olarak ele alır. (Elbette, sadece bütünlük için, herhangi bir değere ayarlanabilen DELIMIDENT ortam değişkeni vardır, ancak Y en güvenlidir - çift tırnakların her zaman sınırlandırılmış tanımlayıcıları çevrelediğini ve tek tırnakların her zaman dizeleri çevrelediğini gösterir.)

MS SQL Server köşeli parantez içine alınmış [sınırlandırılmış tanımlayıcılar] kullanmayı başardığını unutmayın. Bana tuhaf geliyor ve kesinlikle SQL standardının bir parçası değil.


40

İlk cevaba bir şey eklemek için, başka bir tablodan çok az kayıt istediğimizde (bu örnekte sadece bir tane):

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

4
Bu yaklaşım, yalnızca bir sütun seçili olan alt sorgu için geçerlidir. Çok sütunlu alt sorgu durumunda, 'alt sorgu yalnızca bir sütun döndürmelidir' hatası ortaya çıkar. @ Travis'in cevabını benimseyin.
snowfox

34

Veritabanlarının çoğu temel sözdizimini takip eder,

INSERT INTO TABLE_NAME
SELECT COL1, COL2 ...
FROM TABLE_YOU_NEED_TO_TAKE_FROM
;

Ben yani bu sözdizimini izleyin kullanmış Her veritabanı, DB2, SQL Server, MY SQL,PostgresQL


34

Sorgunun bir VALUESparçası yerine, aşağıdaki gibi sorguyu INSERTkullanın SELECT.

INSERT INTO table1 ( column1 , 2, 3... )
SELECT col1, 2, 3... FROM table2

32

Seçme alt sorgusuyla ekleme için iki yaklaşım.

  1. Bir satır ile SELECT alt sorgusu sonuçları döndürme ile .
  2. SELECT alt sorgusu ile sonuçları birden çok satır döndürme .

1. Tek bir satırla SELECT alt sorgusu döndürme sonuçlarıyla yaklaşım .

INSERT INTO <table_name> (<field1>, <field2>, <field3>) 
VALUES ('DUMMY1', (SELECT <field> FROM <table_name> ),'DUMMY2');

Bu durumda, SELECT alt sorgusunun WHERE koşulu veya SUM, MAX, AVG vb.Gibi SQL toplama işlevlerine bağlı olarak yalnızca bir sonuç satırı döndürdüğünü varsayar.

2. SELECT alt sorgusu ile sonuçları birden çok satırla döndürme yaklaşımı .

INSERT INTO <table_name> (<field1>, <field2>, <field3>) 
SELECT 'DUMMY1', <field>, 'DUMMY2' FROM <table_name>;

İkinci yaklaşım her iki durumda da işe yarayacaktır.


29

INSERT INTOParçadaki tüm sütunlar için değer sağlıyorsanız bu, parçadaki sütunları belirtmeden yapılabilir SELECT.

Diyelim ki table1'in iki sütunu var. Bu sorgu çalışmalıdır:

INSERT INTO table1
SELECT  col1, col2
FROM    table2

Bu ÇALIŞMAZ (değeri col2belirtilmez):

INSERT INTO table1
SELECT  col1
FROM    table2

MS SQL Server kullanıyorum. Diğer RDMS'nin nasıl çalıştığını bilmiyorum.


24

Bu, select ile değerleri kullanan başka bir örnektir:

INSERT INTO table1(desc, id, email) 
SELECT "Hello World", 3, email FROM table2 WHERE ...

Eski cevap ve hala yararlı. Oldukça basit ve açık ama ihtiyaçlarımı tam olarak karşılıyor. Teşekkürler!
Sebastian Kaczmarek

21

Tablo sütun dizisi bilindiğinde basit ekleme:

    Insert into Table1
    values(1,2,...)

Basit ekleme söz konusu sütun:

    Insert into Table1(col2,col4)
    values(1,2)

Bir tablonun seçili sütunlarının sayısı (# table2) ekleme tablosuna eşit olduğunda toplu ekleme (Tablo1)

    Insert into Table1 {Column sequence}
    Select * -- column sequence should be same.
       from #table2

Yalnızca bir tablonun istenen sütununa eklemek istediğinizde toplu ekleme (tablo1):

    Insert into Table1 (Column1,Column2 ....Desired Column from Table1)  
    Select Column1,Column2..desired column from #table2
       from #table2

17

Kaynağın birden fazla tablo kullanılarak alındığı başka bir örnek:

INSERT INTO cesc_pf_stmt_ext_wrk( 
  PF_EMP_CODE    ,
  PF_DEPT_CODE   ,
  PF_SEC_CODE    ,
  PF_PROL_NO     ,
  PF_FM_SEQ      ,
  PF_SEQ_NO      ,
  PF_SEP_TAG     ,
  PF_SOURCE) 
SELECT
  PFl_EMP_CODE    ,
  PFl_DEPT_CODE   ,
  PFl_SEC         ,
  PFl_PROL_NO     ,
  PF_FM_SEQ       ,
  PF_SEQ_NO       ,
  PFl_SEP_TAG     ,
  PF_SOURCE
 FROM cesc_pf_stmt_ext,
      cesc_pfl_emp_master
 WHERE pfl_sep_tag LIKE '0'
   AND pfl_emp_code=pf_emp_code(+);

COMMIT;

17

INSERT içine SELECT yan tümcesi için parantez kullanın . Örneğin şöyle:

INSERT INTO Table1 (col1, col2, your_desired_value_from_select_clause, col3)
VALUES (
   'col1_value', 
   'col2_value',
   (SELECT col_Table2 FROM Table2 WHERE IdTable2 = 'your_satisfied_value_for_col_Table2_selected'),
   'col3_value'
);

Teşekkürler @Das Onun için çalışıyor ....
Raj G

16

Birden çok tablodan nasıl ekleyeceğiniz aşağıda açıklanmıştır. Bu özel örnek, çoktan çoğa bir senaryoda bir eşleme tablonuzun bulunduğu yerdir:

insert into StudentCourseMap (StudentId, CourseId) 
SELECT  Student.Id, Course.Id FROM Student, Course 
WHERE Student.Name = 'Paddy Murphy' AND Course.Name = 'Basket weaving for beginners'

(Öğrenci adıyla eşleşmenin birden fazla değer döndürdüğünün farkındayım, ancak fikri anlıyorsunuz. Kimlik bir Kimlik sütunu ve bilinmiyorsa, Kimlik dışında bir şeyle eşleştirmek gerekir.)


14
INSERT INTO yourtable
SELECT fielda, fieldb, fieldc
FROM donortable;

Bu, tüm DBMS'de çalışır


14

SELECT * INTOTabloyu kullanarak tüm sütunları eklemek istiyorsanız bunu deneyebilirsiniz .

SELECT  *
INTO    Table2
FROM    Table1;

13

Aslında SQL Server 2008'de aşağıdakileri tercih ederim:

SELECT Table1.Column1, Table1.Column2, Table2.Column1, Table2.Column2, 'Some String' AS SomeString, 8 AS SomeInt
INTO Table3
FROM Table1 INNER JOIN Table2 ON Table1.Column1 = Table2.Column3

Insert () kümesini ekleme adımını ortadan kaldırır ve sadece tabloya hangi değerlerin gideceğini seçersiniz.


13

Bu benim için çalıştı:

insert into table1 select * from table2

Cümle Oracle'ınkinden biraz farklı.


12

Microsoft SQL Server için, MSDN'de sağlanan SYNTAX'ı yorumlamayı öğrenmenizi öneririm. Google ile sözdizimi aramak her zamankinden daha kolay.

Bu özel durum için,

Google: site ekle: microsoft.com

İlk sonuç http://msdn.microsoft.com/en-us/library/ms174335.aspx olacaktır.

Sayfanın üst kısmında verilen sözdizimini yorumlamakta zorlanıyorsanız, örneğe ilerleyin ("Diğer tablolardan veri eklemek için SEÇ ve YÜRÜT seçeneklerini kullanma").

[ WITH <common_table_expression> [ ,...n ] ]
INSERT 
{
        [ TOP ( expression ) [ PERCENT ] ] 
        [ INTO ] 
        { <object> | rowset_function_limited 
          [ WITH ( <Table_Hint_Limited> [ ...n ] ) ]
        }
    {
        [ ( column_list ) ] 
        [ <OUTPUT Clause> ]
        { VALUES ( { DEFAULT | NULL | expression } [ ,...n ] ) [ ,...n     ] 
        | derived_table       <<<<------- Look here ------------------------
        | execute_statement   <<<<------- Look here ------------------------
        | <dml_table_source>  <<<<------- Look here ------------------------
        | DEFAULT VALUES 
        }
    }
}
[;]

Bu, orada bulunan diğer RDBMS'ler için geçerli olmalıdır. Tüm ürünler IMO'sunun tüm sözdizimini hatırlamanın bir anlamı yoktur.


Tamamen katılmıyorum, yıllardır bu sözdizimi ifadelerine bakıyorum ve yine de bunların başlarını veya kuyruklarını yapamıyorum. Örnekler çok daha kullanışlıdır
reggaeguitar

Bu bir cevap değil, "belgeleri okuyun" diyor ve hepsi bu kadar
reggaeguitar

12
INSERT INTO FIRST_TABLE_NAME (COLUMN_NAME)
SELECT  COLUMN_NAME
FROM    ANOTHER_TABLE_NAME 
WHERE CONDITION;

@ggorlen Bana oldukça açık görünüyor
reggaeguitar

İnceleme sırasında yalnızca kod yanıtı olarak işaretlendi. Yine de burada görüşünüzü görebiliyorum - bu sayfadaki çoğu cevap bağlamında söyleyecek çok şey yok, şimdi doğal ortamında görüyorum.
ggorlen

9
select *
into tmp
from orders

Güzel görünüyor, ancak yalnızca tmp yoksa çalışır (oluşturur ve doldurur). (SQL sever)

Mevcut tmp tablosuna eklemek için:

set identity_insert tmp on

insert tmp 
([OrderID]
      ,[CustomerID]
      ,[EmployeeID]
      ,[OrderDate]
      ,[RequiredDate]
      ,[ShippedDate]
      ,[ShipVia]
      ,[Freight]
      ,[ShipName]
      ,[ShipAddress]
      ,[ShipCity]
      ,[ShipRegion]
      ,[ShipPostalCode]
      ,[ShipCountry] )
      select * from orders

set identity_insert tmp off

9

Diğer tablolardan birden çok kayıt eklemenin en iyi yolu.

INSERT  INTO dbo.Users
            ( UserID ,
              Full_Name ,
              Login_Name ,
              Password
            )
            SELECT  UserID ,
                    Full_Name ,
                    Login_Name ,
                    Password
            FROM    Users_Table
            (INNER JOIN / LEFT JOIN ...)
            (WHERE CONDITION...)
            (OTHER CLAUSE)

2

Birden çok satır eklemek için DEĞERLERİ GİRİŞ yoluna giderseniz, DEĞERLERİ parantez kullanarak kümelere ayırdığınızdan emin olun, bu nedenle:

INSERT INTO `receiving_table`
  (id,
  first_name,
  last_name)
VALUES 
  (1002,'Charles','Babbage'),
  (1003,'George', 'Boole'),
  (1001,'Donald','Chamberlin'),
  (1004,'Alan','Turing'),
  (1005,'My','Widenius');

Aksi takdirde "Sütun sayısı satır 1'deki değer sayısı ile eşleşmez" MySQL nesneleri ve sonunda bu konuda ne yapacağınızı anladığınızda önemsiz bir yazı yazabilirsiniz.


6
Soru " başka bir tablodaki girdiyi kullanarak bir tabloya eklemek " dir. Cevabınız bu soruyu nasıl ele alıyor?
Kalite Katalizörü

3
Ona çok zor olma. Etrafımda dolaşırken sorumu yanıtladı. @CualityCatalyst
Cameron Belt

1

Sütun adı yazmak istemeden bir tabloya bazı veriler eklemek istiyorsanız.

INSERT INTO CUSTOMER_INFO
   (SELECT CUSTOMER_NAME,
           MOBILE_NO,
           ADDRESS
      FROM OWNER_INFO cm
     WHERE ID>100)

Tablolar nerede:

            CUSTOMER_INFO               ||            OWNER_INFO
----------------------------------------||-------------------------------------
CUSTOMER_NAME | MOBILE_NO | ADDRESS     || CUSTOMER_NAME | MOBILE_NO | ADDRESS 
--------------|-----------|---------    || --------------|-----------|--------- 
      A       |     +1    |   DC        ||       B       |     +55   |   RR  

Sonuç:

            CUSTOMER_INFO               ||            OWNER_INFO
----------------------------------------||-------------------------------------
CUSTOMER_NAME | MOBILE_NO | ADDRESS     || CUSTOMER_NAME | MOBILE_NO | ADDRESS 
--------------|-----------|---------    || --------------|-----------|--------- 
      A       |     +1    |   DC        ||       B       |     +55   |   RR
      B       |     +55   |   RR        ||

0

Informix'te Claude'un dediği gibi çalışır:

INSERT INTO table (column1, column2) 
VALUES (value1, value2);    

0

Postgres daha sonra destekliyor: company.monitor'den select * olarak table company.monitor2 oluştur;

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.