web-dev-qa-db-ja.com

SQL挿入ステートメントのテーブル名のエイリアス

値を挿入するテーブルのエイリアス名を指定することはできますか?

ネストされたクエリ内で条件を指定したいのですが、テーブルが冗長すぎます...

これを回すようなもの:

INSERT INTO my_table_with_a_very_long_name (col_a, col_b, col_c)
SELECT foo, bar, baz
FROM other_table
WHERE
  other_table.some_value > 
  (SELECT max(other_value) FROM my_table_with_a_very_long_name);

これに:

INSERT INTO my_table_with_a_very_long_name AS t (col_a, col_b, col_c)
SELECT foo, bar, baz
FROM other_table
WHERE
  other_table.some_value > (SELECT max(other_value) FROM t);

(明らかに私の場合はより長く、いくつかの参照がより多く含まれています)

14
fortran

テーブルにエイリアスを付けるのではなく、テーブル参照のインスタンスにエイリアスを付けます。

これにより、同じ物理テーブルへの参照のインスタンスが複数あるため、自己結合などが可能になります。各ASがそのテーブルに別の場所で新しい名前を付ける場合ではなく、その特定の参照を参照するための単なるエイリアスです。


あなたの場合、2つのショーストッパーがあります...

挿入されるテーブル自体はselectクエリの一部ではなく、たとえばfoobar、またはbazと同じように参照されるセットではありません。したがって、エイリアスを作成することはできません(必要がないため、参照することはできません)。

また、たとえそうであったとしても、エイリアスを介してテーブル全体を参照することはできません。セットを介して繰り返されるクエリの一部として、フィールドを参照します。たとえば、これも機能しません...

SELECT * FROM myTable AS xxx WHERE id = (SELECT MAX(id) FROM xxx)

後者の例は、次を使用して回避できます...

WITH xxx AS (SELECT * FROM myTable) 
SELECT * FROM xx WHERE id = (SELECT MAX(id) FROM xxx)

しかし、それでも最初のポイントに戻ります。挿入されるテーブルは、ステートメントのクエリ部分で参照されることはありません。

近づくことを考える唯一の方法は、ビューを作成することです...

11
MatBailie

答えは[〜#〜] no [〜#〜]だと思います。 ASの後にtableNameはありません

INSERT INTO table [ ( column [, ...] ) ]
    { DEFAULT VALUES | VALUES ( { expression | DEFAULT } [, ...] ) [, ...] | query }
    [ RETURNING * | output_expression [ [ AS ] output_name ] [, ...] ]

参照

更新

AS句は バージョン9.5 の時点でPostgreSQLの一部になりましたが、@ MatBailieが上記で述べたように、ネストはINSERTクエリとSELECTサブクエリを個別に実行しないと、問題が発生します。例えば。:

> CREATE TABLE foo (id int, name text);
CREATE TABLE
> INSERT INTO foo VALUES (1, 'alice'), (2, 'bob'), (3, 'claire');
INSERT 0 3
> INSERT INTO foo AS f (SELECT f.* from f);
ERROR:  relation "f" does not exist
LINE 1: INSERT INTO foo AS f (SELECT f.* from f);
                                              ^

-- Next line works, but is confusing. Pick distinct aliases in real life.
-- I chose the same 'f' to illustrate that the sub-select 
-- really is separate.
> INSERT INTO foo AS f (SELECT f.* from foo f); 
INSERT 0 3
> > SELECT * FROM foo;
 id |  name
----+--------
  1 | alice
  2 | bob
  3 | claire
  1 | alice
  2 | bob
  3 | claire
(6 rows)
7
John Woo

他の人が言っているように、INSERT INTOステートメントの一部として名前をエイリアスすることはできません。 WHEREステートメントのサブクエリに配置する必要があります。

INSERT INTO my_table_with_a_very_long_name (col_a, col_b, col_c)
SELECT foo, bar, baz
FROM other_table
WHERE
  other_table.some_value > (SELECT max(other_value) FROM 
      my_table_with_a_very_long_name AS t);
0
RPh_Coder