我可以将此 INSERT 和 DELETE 查询放入单个 INSERT 查询中吗

Can I put this INSERT and DELETE query into a single INSERT query

如何将其放入一个查询中,关键是按名称对艺术家进行分组时我需要考虑 artist 中的所有行,但我不想保留 [=12] 中的行=] table 如果它已经在 mbartist_discogsartist table 中。 (我使用的是 Postgres 9.3)

INSERT INTO artist_nodup
SELECT
min(a1.id) as id,
a1.name
FROM artist  a1
GROUP BY a1.name
HAVING COUNT(*)=1
;

DELETE
FROM artist_nodup T1
WHERE exists
( select 1
   from mbartist_discogsartist T2
  where t1.id = t2.discogs_id
)
;

您可以创建 Stored Procedure.

CREATE PROCEDURE sp_InsertDelete
AS
BEGIN
    INSERT INTO artist_nodup
    SELECT
    min(a1.id) as id,
    a1.name
    FROM artist  a1
    GROUP BY a1.name
    HAVING COUNT(*)=1
    ;
    GO
    DELETE
    FROM artist_nodup T1
    WHERE exists
    ( select 1
       from mbartist_discogsartist T2
      where t1.id = t2.discogs_id
    )
    ;
END

要同时使用这两个查询,您可以调用新创建的存储过程:EXECUTE sp_InsertDelete


或者您可以在 artist_nodup table 上创建 TRIGGER。当某些内容将被插入到 artist_nodup table 时,它会自动使用删除查询。

注意:如果您只需要在提供插入查询后使用删除查询,这对您不起作用,因为这个删除查询总是在插入任何内容后使用。

CREATE TRIGGER AutoDelete ON artist_nodup 
AFTER INSERT 
AS
BEGIN
     DELETE
     FROM artist_nodup T1
     WHERE exists
     ( select 1
        from mbartist_discogsartist T2
       where t1.id = t2.discogs_id
     )
     ;   
END;

如果足以避免 INSERT 中的冗余行并且也不需要从 artist_nodup 中删除以前存在的行:

INSERT INTO artist_nodup
SELECT a.id, a.name
FROM   artist a
LEFT   JOIN artist a2 ON a2.name = a.name AND a2.id <> a.id
LEFT   JOIN mbartist_discogsartist m ON m.discogs_id = a.id
WHERE  a2.name IS NULL
AND    m.discogs_id IS NULL;

第一个 LEFT JOIN 排除了 artist 中存在其他同名行的行。
第二个 LEFT JOIN 排除 artist 中存在匹配 id 的行 mbartist_discogsartist替换后来 DELETE).

LEFT JOIN / IS NULL 是执行此操作的几种技术之一:

  • Select rows which are not present in other table

如果您还想排除 artist_nodup 中预先存在的行:

...
LEFT JOIN artist_nodup an ON an.name = a.name
...
AND an.name IS NULL

你学会了......