web-dev-qa-db-ja.com

JOINを使用するときにMS Accessで削除する方法は?

MS AccessでDELETE句を使用しようとしていますが、JOIN句も使用すると問題が発生します。これはDISTINCTROWキーワードを使用して達成できることに気づきました。

たとえば、次のSQLステートメントは削除を許可しません。

DELETE Table1.*
FROM Table1 INNER JOIN Table2 ON Table1.Name=Table2.Name;

ただし、このステートメントは以下を行います

DELETE DISTINCTROW Table1.*
FROM Table1 INNER JOIN Table2 ON Table1.Name=Table2.Name;
  • DELETEキーワードを使用するときにDISTINCTROWが機能するのはなぜですか?
  • より具体的には、これを要求するためにJETエンジンで何が起きているのでしょうか?
24
Delete Table1.*
From Table1
Where Exists( Select 1 From Table2 Where Table2.Name = Table1.Name ) = True

私の答えを拡張するために、公式のSQL仕様では、あいまいな結果を作成する可能性があるため、アクションクエリでの結合の使用を規定していません。したがって、ここにあるようなアクションクエリでJoinsを使用するのを避けることができれば、それはより良い(そしてAccessはずっと幸せです)。 AccessがDISTINCTROWを必要とする理由は、2つのテーブル間の結合がTable1行の複製を作成する(つまり、Table2に複数の関連する行がある)ため、Accessが混乱する可能性があるためです。また、Joinを使用しようとして主キーが存在しないと、Accessが動作しなくなることもわかりました。一般に、可能な場合はアクションクエリでの結合を避けることをお勧めします。

24
Thomas

注意すべき問題が1つあります。これは、テーブル/クエリエイリアスでは機能しません。

DELETE a.*
from tblA as A
where exists (select 1 from tblB as B where a.id=b.id)

TblAのすべてのレコードを削除します! tblAとtblBのエイリアスを別々に使用して試してみました-同じ結果(Access 2010)。

SELECTでも発生します(削除する前によく使用します)...

3
MarcusFey
DELETE a.*
FROM tblA AS A
WHERE EXISTS (SELECT 1 FROM tblB AS B WHERE a.id=b.id)

これを試して

DELETE tblA 
FROM tblB  
WHERE EXISTS (SELECT * FROM tblA AS A,tblB AS B WHERE A.id=B.id)
0
user7047561