10 Stimmen

Wie kann ich die Anzahl der Zeilen bei einem DELETE mit DB2 begrenzen?

Ich möchte eine Sicherheit für eine sensible Tabelle hinzufügen, wenn ich Zeilen mit einer SQL-Anfrage in einer DB2-Tabelle lösche.

Ich möchte die Art und Weise nachahmen, in der MySQL es erlaubt, die Anzahl der in einer SQL-Anfrage gelöschten Zeilen zu begrenzen.

Im Grunde möchte ich dies mit DB2 tun:

DELETE FROM table WHERE info = '1' LIMIT 1

Gibt es eine Möglichkeit, dies mit DB2 zu tun?

10voto

Konstantinos Punkte 12825
delete from table where id in (select id from table where info = '1' order by id fetch first 1 rows only)

6voto

bhamby Punkte 14694

Das hängt wirklich von Ihrer Plattform ab.

Wenn Sie DB2 unter Linux/Unix/Windows verwenden, können Sie einfach einen Select erstellen, der die gewünschten Zeilen abruft, und diesen als Unterabfrage für Ihren Löschvorgang verwenden, und DB2 kann die Ergebnisse Ihres Selects löschen. Zum Beispiel so:

DELETE FROM (
    SELECT 1
    FROM table
    WHERE info = '1'
    ORDER BY your_key_columns
    FETCH FIRST ROW ONLY
) AS A
;

Wenn Sie mit DB2 für z/OS arbeiten, funktioniert diese Syntax leider nicht. Aber Sie können Ihre Primärschlüssel verwenden, um im Grunde das Gleiche zu tun (dies funktioniert auch unter LUW):

DELETE FROM table
WHERE (info, key2) IN (
    SELECT info, key2
    FROM table
    WHERE info = 1
    ORDER BY key2
    FETCH FIRST ROW ONLY
);

Hier ist ein Beispielskript, das seine Verwendung demonstriert:

DECLARE GLOBAL TEMPORARY TABLE SESSION.TEST(
     ID INT
    ,RN INT
) ON COMMIT PRESERVE ROWS;

INSERT INTO SESSION.TEST 
    SELECT 1,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 1,2 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 1,3 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 1,4 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 1,5 FROM SYSIBM.SYSDUMMY1 UNION ALL

    SELECT 2,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 2,2 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 2,3 FROM SYSIBM.SYSDUMMY1 UNION ALL

    SELECT 3,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 3,2 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 3,3 FROM SYSIBM.SYSDUMMY1 UNION ALL

    SELECT 4,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 4,2 FROM SYSIBM.SYSDUMMY1 UNION ALL

    SELECT 5,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 6,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 7,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 8,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 9,1 FROM SYSIBM.SYSDUMMY1 UNION ALL
    SELECT 10,1 FROM SYSIBM.SYSDUMMY1
;

SELECT * FROM SESSION.TEST ORDER BY ID, RN;

-- LUW Version
DELETE FROM (
    SELECT 1
    FROM SESSION.TEST
    WHERE ID = 1
    ORDER BY RN
    FETCH FIRST ROW ONLY
) AS A
;

--Mainframe version
DELETE FROM SESSION.TEST
WHERE (ID, RN) IN (
    SELECT ID, RN
    FROM SESSION.TEST
    WHERE ID = 1
    ORDER BY RN
    FETCH FIRST ROW ONLY
);

SELECT * FROM SESSION.TEST ORDER BY ID, RN;

DROP TABLE SESSION.TEST;

1voto

keV Punkte 11

Bei IBMi DB2:

DELETE FROM table WHERE RRN(table) in 
(SELECT RRN(table) FROM table WHERE col1 = '1' AND col2 = '2' FETCH FIRST 5 ROWS ONLY)

1voto

bluefoot Punkte 9682

Wenn Ihr Primärschlüssel mehrere Werte hat oder Sie einfach mehrere Werte als Bedingung benötigen, ist dies die Abfrage, die funktioniert:

DELETE FROM TABLE
WHERE (COLUMN1, COLUMN2) IN (
    SELECT COLUMN1, COLUMN2 FROM TABLE
    WHERE SOME_COLUMN='THIS'
    AND SOME_OTHER_COLUMN LIKE 'THAT%'
    FETCH FIRST 10 ROWS ONLY)

0voto

Wie lautet diese Abfrage?

delete from table D where exists 
 ( select * from ( select * from table M fetch first 10 rows only ) as M
   where M.object_id = D.object_id )

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X