ABAP INSERT für interne Tabellen: Zeilen einfügen

kategorie
ABAP-Statements
Veröffentlicht
autor
Johannes

Die INSERT-Anweisung für interne Tabellen fügt eine oder mehrere Zeilen an einer bestimmten Position oder gemäß dem Tabellenschlüssel ein. Im Gegensatz zu APPEND, das immer am Ende anfügt, ermöglicht INSERT präzise Kontrolle über die Einfügeposition.

Syntax

1. Zeile per Index einfügen

INSERT <zeile> INTO <interne_tabelle> INDEX <index>.

2. Zeile gemäß Schlüssel einfügen

INSERT <zeile> INTO TABLE <interne_tabelle>.

3. Mehrere Zeilen einfügen

INSERT LINES OF <quelltabelle> INTO TABLE <zieltabelle>.
INSERT LINES OF <quelltabelle> FROM <von> TO <bis> INTO <zieltabelle> INDEX <index>.

4. Initialzeile einfügen

INSERT INITIAL LINE INTO <interne_tabelle> INDEX <index>.
INSERT INITIAL LINE INTO TABLE <interne_tabelle>.

Systemfelder

Nach INSERT:

  • sy-subrc:

    • 0: Zeile erfolgreich eingefügt
    • 4: Zeile konnte nicht eingefügt werden (z.B. Duplikat bei UNIQUE KEY)
  • sy-tabix: Index der eingefügten Zeile (bei INDEX-Variante)

Beispiele

1. Zeile per Index einfügen

DATA: lt_names TYPE TABLE OF string.
lt_names = VALUE #( ( `Anna` ) ( `Clara` ) ( `David` ) ).
" Bernd an Position 2 einfügen
INSERT `Bernd` INTO lt_names INDEX 2.
" Ergebnis: Anna, Bernd, Clara, David
LOOP AT lt_names INTO DATA(lv_name).
WRITE: / sy-tabix, lv_name.
ENDLOOP.

2. Am Anfang einfügen

DATA: lt_numbers TYPE TABLE OF i.
lt_numbers = VALUE #( ( 2 ) ( 3 ) ( 4 ) ).
" 1 am Anfang einfügen
INSERT 1 INTO lt_numbers INDEX 1.
" Ergebnis: 1, 2, 3, 4

3. Struktur einfügen

TYPES: BEGIN OF ty_customer,
id TYPE i,
name TYPE string,
city TYPE string,
END OF ty_customer.
DATA: lt_customers TYPE TABLE OF ty_customer,
ls_customer TYPE ty_customer.
lt_customers = VALUE #(
( id = 1 name = 'Müller' city = 'Berlin' )
( id = 3 name = 'Weber' city = 'Hamburg' )
).
" Neuen Kunden an Position 2 einfügen
ls_customer = VALUE #( id = 2 name = 'Schmidt' city = 'München' ).
INSERT ls_customer INTO lt_customers INDEX 2.
" Ergebnis: Müller (1), Schmidt (2), Weber (3)

4. INSERT INTO TABLE (nach Schlüssel)

DATA: lt_sorted TYPE SORTED TABLE OF ty_customer
WITH UNIQUE KEY id.
lt_sorted = VALUE #(
( id = 1 name = 'Müller' city = 'Berlin' )
( id = 3 name = 'Weber' city = 'Hamburg' )
).
" Wird automatisch an richtiger Position eingefügt (nach Schlüssel sortiert)
ls_customer = VALUE #( id = 2 name = 'Schmidt' city = 'München' ).
INSERT ls_customer INTO TABLE lt_sorted.
IF sy-subrc = 0.
WRITE: / 'Erfolgreich eingefügt an Position:', sy-tabix.
ENDIF.
" Ergebnis: Automatisch zwischen ID 1 und 3 einsortiert

5. Duplikate verhindern (UNIQUE KEY)

DATA: lt_unique TYPE SORTED TABLE OF ty_customer
WITH UNIQUE KEY id.
lt_unique = VALUE #( ( id = 1 name = 'Müller' city = 'Berlin' ) ).
" Versuch, Duplikat einzufügen
ls_customer = VALUE #( id = 1 name = 'Neu' city = 'Köln' ).
INSERT ls_customer INTO TABLE lt_unique.
IF sy-subrc = 4.
WRITE: / 'Duplikat! Zeile nicht eingefügt.'.
ENDIF.

6. HASHED TABLE

DATA: lt_hashed TYPE HASHED TABLE OF ty_customer
WITH UNIQUE KEY id.
" Bei HASHED TABLE: Immer INSERT INTO TABLE (kein INDEX!)
ls_customer = VALUE #( id = 5 name = 'Bauer' city = 'Dresden' ).
INSERT ls_customer INTO TABLE lt_hashed.
IF sy-subrc = 0.
WRITE: / 'In Hash-Tabelle eingefügt.'.
ENDIF.

7. Mehrere Zeilen einfügen (LINES OF)

DATA: lt_source TYPE TABLE OF string,
lt_target TYPE TABLE OF string.
lt_source = VALUE #( ( `Neu1` ) ( `Neu2` ) ( `Neu3` ) ).
lt_target = VALUE #( ( `Alt1` ) ( `Alt2` ) ).
" Alle Zeilen aus source in target einfügen (am Ende)
INSERT LINES OF lt_source INTO TABLE lt_target.
" Ergebnis: Alt1, Alt2, Neu1, Neu2, Neu3

8. LINES OF mit INDEX

DATA: lt_source TYPE TABLE OF string,
lt_target TYPE TABLE OF string.
lt_source = VALUE #( ( `X` ) ( `Y` ) ( `Z` ) ).
lt_target = VALUE #( ( `A` ) ( `B` ) ( `C` ) ).
" Zeilen an Position 2 einfügen
INSERT LINES OF lt_source INTO lt_target INDEX 2.
" Ergebnis: A, X, Y, Z, B, C

9. LINES OF mit FROM…TO

DATA: lt_source TYPE TABLE OF i,
lt_target TYPE TABLE OF i.
lt_source = VALUE #( ( 10 ) ( 20 ) ( 30 ) ( 40 ) ( 50 ) ).
lt_target = VALUE #( ( 1 ) ( 2 ) ( 3 ) ).
" Nur Zeilen 2-4 aus source einfügen
INSERT LINES OF lt_source FROM 2 TO 4 INTO TABLE lt_target.
" Ergebnis: 1, 2, 3, 20, 30, 40

10. INITIAL LINE einfügen

DATA: lt_customers TYPE TABLE OF ty_customer.
lt_customers = VALUE #(
( id = 1 name = 'Müller' city = 'Berlin' )
).
" Leere Zeile an Position 1 einfügen
INSERT INITIAL LINE INTO lt_customers INDEX 1.
" Ergebnis: (leer), Müller
LOOP AT lt_customers INTO DATA(ls_cust).
WRITE: / ls_cust-id, ls_cust-name.
ENDLOOP.

11. INSERT mit ASSIGNING

DATA: lt_customers TYPE TABLE OF ty_customer.
" Zeile einfügen und direkt bearbeiten
INSERT VALUE #( id = 99 ) INTO TABLE lt_customers
ASSIGNING FIELD-SYMBOL(<ls_new>).
IF sy-subrc = 0.
<ls_new>-name = 'Neu erstellt'.
<ls_new>-city = 'Unbekannt'.
ENDIF.

12. INSERT mit REFERENCE INTO

DATA: lt_data TYPE TABLE OF ty_customer,
lr_line TYPE REF TO ty_customer.
INSERT VALUE #( id = 100 name = 'Test' ) INTO TABLE lt_data
REFERENCE INTO lr_line.
IF sy-subrc = 0.
lr_line->city = 'Referenz-Update'.
ENDIF.

13. INSERT im LOOP (Vorsicht!)

" ACHTUNG: INSERT im LOOP kann zu Endlosschleifen führen!
DATA: lt_numbers TYPE TABLE OF i.
lt_numbers = VALUE #( ( 1 ) ( 2 ) ( 3 ) ).
" FALSCH - Kann Endlosschleife verursachen!
" LOOP AT lt_numbers INTO DATA(lv_num).
" IF lv_num = 2.
" INSERT 99 INTO lt_numbers INDEX sy-tabix.
" ENDIF.
" ENDLOOP.
" RICHTIG: Änderungen sammeln und danach einfügen
DATA: lt_to_insert TYPE TABLE OF i.
LOOP AT lt_numbers INTO DATA(lv_num).
IF lv_num = 2.
APPEND 99 TO lt_to_insert.
ENDIF.
ENDLOOP.
INSERT LINES OF lt_to_insert INTO lt_numbers INDEX 2.

14. INSERT für verschiedene Tabellentypen

TabellentypINSERT … INDEXINSERT INTO TABLE
STANDARDJaJa (am Ende)
SORTEDNein (Syntaxfehler)Ja (sortiert ein)
HASHEDNein (Syntaxfehler)Ja (nach Hash)
" STANDARD TABLE: Beide Varianten möglich
DATA: lt_standard TYPE STANDARD TABLE OF ty_customer.
INSERT ls_customer INTO lt_standard INDEX 1. " OK
INSERT ls_customer INTO TABLE lt_standard. " OK (am Ende)
" SORTED TABLE: Nur INTO TABLE
DATA: lt_sorted TYPE SORTED TABLE OF ty_customer WITH UNIQUE KEY id.
" INSERT ls INTO lt_sorted INDEX 1. " SYNTAXFEHLER!
INSERT ls_customer INTO TABLE lt_sorted. " OK (sortiert ein)
" HASHED TABLE: Nur INTO TABLE
DATA: lt_hashed TYPE HASHED TABLE OF ty_customer WITH UNIQUE KEY id.
" INSERT ls INTO lt_hashed INDEX 1. " SYNTAXFEHLER!
INSERT ls_customer INTO TABLE lt_hashed. " OK

INSERT vs. APPEND

AspektINSERTAPPEND
PositionBeliebig (INDEX) oder nach SchlüsselImmer am Ende
SORTED TABLEINTO TABLE (sortiert ein)Nur wenn Sortierung erhalten
HASHED TABLEINTO TABLENicht möglich
Duplikatprüfungsy-subrc = 4 bei UNIQUE KEYKeine (außer SORTED)
PerformanceBei INDEX: O(n)O(1)
" APPEND: Immer am Ende
APPEND ls_customer TO lt_standard.
" INSERT INDEX: An bestimmter Position
INSERT ls_customer INTO lt_standard INDEX 1.
" INSERT INTO TABLE: Nach Tabellentyp
INSERT ls_customer INTO TABLE lt_sorted. " Sortiert automatisch ein

INSERT vs. MODIFY

" INSERT: Fügt neue Zeile ein (Fehler bei Duplikat)
INSERT ls_customer INTO TABLE lt_unique.
" MODIFY: Fügt ein ODER aktualisiert bestehende
MODIFY TABLE lt_unique FROM ls_customer.

Performance-Tipps

  1. Massen-Insert mit LINES OF:

    " LANGSAM: Einzelne INSERTs
    LOOP AT lt_source INTO ls_line.
    INSERT ls_line INTO TABLE lt_target.
    ENDLOOP.
    " SCHNELLER: LINES OF
    INSERT LINES OF lt_source INTO TABLE lt_target.
  2. SORTED vs. STANDARD für häufige Inserts:

    " Bei vielen Inserts: STANDARD TABLE sammeln, dann sortieren
    DATA: lt_collect TYPE STANDARD TABLE OF ty_data.
    LOOP AT lt_input INTO ls_input.
    APPEND ls_input TO lt_collect.
    ENDLOOP.
    SORT lt_collect BY key_field.
    DELETE ADJACENT DUPLICATES FROM lt_collect COMPARING key_field.
  3. INDEX-Insert von hinten:

    " Bei mehreren Index-Inserts: Von hinten nach vorne
    " um Verschiebungen zu minimieren
    INSERT 'C' INTO lt_names INDEX 3.
    INSERT 'B' INTO lt_names INDEX 2.
    INSERT 'A' INTO lt_names INDEX 1.

Wichtige Hinweise / Best Practice

  • INSERT ... INDEX nur für STANDARD TABLE möglich.
  • INSERT INTO TABLE respektiert den Tabellenschlüssel (sortiert bei SORTED, hasht bei HASHED).
  • Bei UNIQUE KEY: Prüfen Sie sy-subrc für Duplikaterkennung.
  • Vermeiden Sie INSERT im LOOP AT – Gefahr von Endlosschleifen!
  • Nutzen Sie LINES OF für Massen-Inserts (performanter als Einzelinserts).
  • ASSIGNING und REFERENCE INTO ermöglichen direkten Zugriff auf die eingefügte Zeile.
  • Für Datenbanktabellen verwenden Sie INSERT INTO dbtab.
  • APPEND ist schneller, wenn die Position egal ist (am Ende).
  • MODIFY kombiniert INSERT und UPDATE in einer Anweisung.
  • Bei SORTED TABLE wird automatisch an der korrekten Position eingefügt.