插入...值(SELECT ... FROM ...)

时间:2020-03-05 18:42:47  来源:igfitidea点击:

我正在尝试使用另一个表的输入将表" INSERT INTO"。尽管对于许多数据库引擎来说这是完全可行的,但我似乎总是很难记住当今SQL引擎(MySQL,Oracle,SQL Server,Informix和DB2)的正确语法。

是否有来自SQL标准(例如SQL-92)的Silver-bullet语法,该语法可让我插入值而无需担心基础数据库?

解决方案

回答

尝试:

INSERT INTO table1 ( column1 )
SELECT  col1
FROM    table2

这是标准的ANSI SQL,可以在任何DBMS上使用

它绝对适用于:

  • 甲骨文
  • MS SQL服务器
  • 的MySQL
  • Postgres
  • SQLite v3
  • Teradata
  • DB2
  • Sybase公司
  • Vertica
  • 数据库
  • H2
  • AWS RedShift
  • SAP HANA

回答

@ Shadow_x99:应该可以,并且还可以有多个列和其他数据:

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

编辑:我应该提到,我只在Access,SQL 2000/2005 / Express,MySQL和PostgreSQL中使用了这种语法,因此应该将它们包括在内。评论者指出它将与SQLite3一起使用。

回答

我看到的两个答案都特别适合在Informix中使用,基本上都是标准SQL。即,表示法:

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

与Informix以及所有DBMS配合使用都很好。 (从5年前开始,MySQL并不总是支持这种东西;现在,它已经对这种标准SQL语法提供了不错的支持,并且AFAIK可以在这种表示法上正常工作。)列列表是可选的,但按顺序指示目标列,因此SELECT结果的第一列将进入列出的第一列,依此类推。在没有列列表的情况下,SELECT结果的第一列将进入目标表的第一列。

系统之间可能会有所不同的是,用于标识不同数据库中的表的表示法是该标准对数据库间(更不用说DBMS间)操作了。使用Informix,可以使用以下表示法来标识表:

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

也就是说,我们可以指定一个数据库,如果不在当前服务器中,则可以选择标识承载该数据库的服务器,然后是可选的所有者,点,最后是实际的表名。 SQL标准使用术语架构来表示Informix称为所有者。因此,在Informix中,以下任何一种表示法都可以标识一个表:

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

所有者通常不需要被报价;但是,如果确实使用引号,则需要正确拼写所有者名称,这会区分大小写。那是:

someone.table
"someone".table
SOMEONE.table

都标识同一张表。使用Informix,使用MODE ANSI数据库会有一个轻度的麻烦,其中所有者名称通常会转换为大写(informix是例外)。也就是说,在MODE ANSI数据库(不常用)中,我们可以编写:

CREATE TABLE someone.table ( ... )

并且系统目录中的所有者名称将为" SOMEONE",而不是" someone"。如果将所有者名称用双引号引起来,则其作用类似于分隔标识符。使用标准SQL,分隔符可以在许多地方使用。使用Informix,我们只能在所有者名称周围使用它们-在其他情况下,Informix会将单引号和双引号字符串都视为字符串,而不是将单引号字符串和字符串分开以及将双引号字符串作为分隔标识符。 (当然,为了完整起见,可以将环境变量DELIMIDENT设置为任何值,但是Y最安全地指示双引号始终包围定界标识符,单引号始终包围字符串。)

请注意,MS SQL Server设法使用方括号中包含的[定界标识符]。在我看来,这很奇怪,并且肯定不是SQL标准的一部分。