INSERT INTO允许SELECT使用不存在的列

时间:2016-11-02 16:27:50

标签: sql sql-server tsql

执行以下操作时:

CREATE TABLE TableA
(
    A1 INT,
    A2 INT
)

INSERT INTO TableA (A1, A2) VALUES (1, 2), (3, 4);

CREATE TABLE #TempTable1 (ColumnA INT, ColumnB INT);
CREATE TABLE #TempTable2 (ColumnA INT, ColumnB INT);

INSERT INTO #TempTable1 (ColumnA, ColumnB) VALUES (1, 2);

INSERT INTO #TempTable2
    SELECT A1, A2
    FROM TableA
    WHERE A1 IN (SELECT ColumnA FROM #TempTable1);

SELECT * FROM TableA;
SELECT * FROM #TempTable1;
SELECT * FROM #TempTable2;

结果如下:

TableA
A1  A2
1   2
3   4

#TempTable1
ColumnA ColumnB
1       2

#TempTable2
ColumnA ColumnB
1       2

但是,如果我更改#TempTable2插入语句,以便它从#TempTable1中选择一个不存在的列A1:

INSERT INTO #TempTable2
    SELECT A1, A2
    FROM TableA
    WHERE A1 IN (SELECT A1 FROM #TempTable1);

然后#TempTable2包含来自TableA的所有数据:

ColumnA ColumnB
1       2
3       4

我想知道为什么执行INSERT语句不会产生错误,因为#TempTable1中不存在列A1。例如,如果我尝试添加以下语句:

SELECT A1 FROM #TempTable1;

我明白了:

Invalid column name 'A1'.

3 个答案:

答案 0 :(得分:3)

它被称为require 'csv' namespace :import_ailment do desc "Import ailment from a CSV file" task ailments: :environment do CSV.foreach("ailments.csv") do |row| name, description, shopping_list, price = row Ailment.create(name: name, description: description, shopping_list: shopping_list, price: price) end end end 。引用correlated sub-query

中的外部查询列

Sub-Query是从外部查询(即)A1引用的。因此,当您一起执行查询时,它正在工作,当您单独执行时,它无法正常工作

它将被解释为

TableA

通常在使用SELECT A1, A2 FROM TableA A WHERE A1 IN (SELECT A.A1 -- Here check the alias A FROM #TempTable1); 时,查询将与EXISTS/NOT EXISTS子句相关联。

where

在您的示例中,它在select * from tableA A where exists (select 1 from tableB B where A.Id = B.Id -- A.Id is referred from tableA )

中引用

答案 1 :(得分:2)

虽然其他答案已经回答了为什么你会得到你所得到的结果,但我认为还有另外一个方面值得讨论:这是你应该使用表别名的一个很好的例子。

如果你给代码别名如下,你会收到你期望的错误:

INSERT INTO #TempTable2
    SELECT a.A1, a.A2
    FROM TableA a
    WHERE a.A1 IN (SELECT t.A1 FROM #TempTable1 t);

如果没有别名,SQL Server(和其他DBMS产品)将很乐意默认为与您提供的名称匹配的一列。当人们完全按照你所做的去做时,这会导致错误,但却没有注意到问题。如果使用别名,您只会收到错误,注意问题并更正错误。

答案 2 :(得分:1)

fit <- arima0(y, order = c(1, 0, 0), xreg = X)

在此查询中INSERT INTO #TempTable2 SELECT A1, A2 FROM TableA WHERE A1 IN (SELECT A1 FROM #TempTable1); 是子查询。在SELECT A1 FROM #TempTable1中找不到A1,但是您将其用作#TempTable1的每一行的子查询,因此A1被称为从上表中获取的值。您的子查询等效于TableA,因为A1是每次执行子查询时的常量值。