Die ASSIGN-Anweisung erlaubte es bisher, mit Offset/Längenangaben über Feldgrenzen hinaus zu adressieren. Einen Laufzeitfehler gab es nur dann, wenn über die Grenzen des Datensegments hinaus adressiert wurde. Feldübergreifende Offset/Längenzugriffe bei ASSIGN konnten beispielsweise sinnvoll zur Bearbeitung von Wiederholungsgruppen eingesetzt werden.
Mit Unicode ist dies allerdings problematisch, da nicht mehr sichergestellt ist, daß feldüberschreitende Offset- oder Längenangaben sowohl unter US als auch in NUS einheitlich und sinnvoll als Bytes oder Zeichen interpretiert werden können. Aus diesem Grund wurde die ASSIGN-Anweisung um die Zusätze RANGE und INCREMENT erweitert, während der Zusatz CASTING nunmehr alle Varianten dieser Anweisung unterstützt. Der RANGE-Zusatz wird für alle gültigen Varianten von ASSIGN angeboten und kann mit dem Zusatz CASTING kombiniert werden.
Zusatz RANGE
ASSIGN feld1 TO <fs> RANGE feld2.
Dieser Zusatz setzt explizit die Range-Grenzen. Dadurch ist es möglich, über Feldgrenzen hinaus zu adressieren, um beispielsweise mit der Anweisung ASSIGN INCREMENT Wiederholungsgruppen zu verarbeiten.
ASSIGN feld INCREMENT n TO <fs>.
Das Feldsymbol wird ausgehend von der durch feld bestimmten Position um n mal die Länge von feld weitergesetzt.
Zunächst wird aus der Länge von feld und der INCREMENT-Angabe der Bereich für den Zugriff entsprechend ASSIGN fld+n*sizeof[feld] (sizeof[fld]) TO <fs> bestimmt. Der angesprochene Bereich muß innerhalb der Range-Grenzen liegen. Kann die Zuweisung nicht durchgeführt werden, weil die Range-Grenzen verletzt wurden, so wird SY-SUBRC > 0 gesetzt und das Feldsymbol bleibt unverändert.
Die Range-Grenzen für ASSIGN feld INCREMENT n TO <fs> werden genau so wie bei ASSGIN feld TO <f> bestimmt. Die INCREMENT-Angabe hat daher keinen Einfluß auf die Bestimmung der Range-Grenzen.
Beispiel
* Schleife über ein elementares Feld
DATA: c(10) TYPE C VALUE 'abcdefghij'.
FIELD-SYMBOLS: <cf> TYPE C.
ASSIGN c(2) TO <cf>. "Range-Grenzen c =
DO 5 TIMES. "Feldgrenzen von cf
WRITE / <cf>.
ASSIGN <cf> INCREMENT 1 TO <c>. "Gleiche Grenzen <c>
* ASSIGN <c>+2 TO <cf>. "Wie ASSIGN INCREMENT
ENDDO.
* Strukturierte Wiederholungsgruppe
TYPES: BEGIN OF comp,
f1 type string,
...
END OF comp.
DATA: BEGIN OF stru,
x1(1) TYPE x,
k1 TYPE comp,
k2 TYPE comp,
k3 TYPE comp,
k4 TYPE comp,
END OF stru.
FIELD-SYMBOLS: <comp> TYPE comp.
ASSIGN stru-k1 TO <comp> RANGE stru.
* Range-Grenzen feldübergreifend festlegen
DO 4 TIMES.
...
ASSIGN <comp> INCREMENT 1 TO <comp>.
ENDDO.
* Dynamischer Zugriff auf ein
* Element einer Wiederholungsgruppe
DATA: BEGIN OF stru,
x1(1) TYPE x,
k1 TYPE comp,
k2 TYPE comp,
k3 TYPE comp,
k4 TYPE comp,
END OF stru,
incr TYPE i.
FIELD-SYMBOLS: <comp> TYPE comp.
incr = 4 - 1.
ASSIGN stru-k1 INCREMENT incr TO <comp> RANGE stru.
...
* <comp> steht jetzt auf stru-k4
Zusatz CASTING
Bei allen Varianten der Anweisung ASSIGN ist der Zusatz CASTING erlaubt:
ASSIGN feld TO <fs> CASTING.
ASSIGN feld TO <fs> CASTING TYPE type.
ASSIGN feld TO <fs> CASTING TYPE (typename)
ASSIGN feld TO <fs> CASTING LIKE fld.
ASSIGN feld TO <fs> CASTING DECIMALS dec.
Durch ASSIGN ... CASTING ist es möglich, den Inhalt eines Felds über ein Feldsymbol als einen Wert eines anderen Typs zu betrachten. Eine Anwendung dieser Anweisung besteht beispielsweise darin, durch Casts auf verschiedene Typen unterschiedliche Sichten auf eine Struktur zur Verfügung zu stellen.
Eine verbreitete ABAP-Technik besteht darin, C-Felder oder Strukturen als Container zum Speichern von Strukturen verschiedener, oft erst zur Laufzeit bekannter Typen zu verwenden. Die Selektion von Teilkomponenten der Struktur erfolgt dann durch Offset/Längenzugriffe auf den Container. Da diese Technik mit Unicode nicht mehr funktioniert, kann alternativ ein vorhandener Speicherbereich mittels ASSIGN ... CASTING über ein Feldsymbol als Container mit passender Typisierung betrachtet werden. Im nachfolgenden Beispiel wird ein bestimmtes Feld der Datenbanktabelle X031L gelesen, wobei Feld- und Tabellenname erst zur Laufzeit angegeben werden.
Beispiel
* Lesen eines Feldes der Tabelle X031L
PARAMETERS:
TAB_NAME LIKE SY-TNAME, "Tabellenname
TAB_COMP LIKE X031L-FIELDNAME, "Feldname
ANZAHL TYPE I DEFAULT 10. "Zeilenanzahl
DATA:
BEGIN OF BUFFER,
ALIGNMENT TYPE F, "Alignment
C(8000) TYPE C, "Tabelleninhalt
END OF BUFFER.
FIELD-SYMBOLS: <WA> TYPE ANY,
<COMP> TYPE ANY.
* Feldsymbol mit passender Typisierung
* auf Pufferbereich setzen
ASSIGN BUFFER TO <WA> CASTING TYPE (TAB_NAME).
SELECT * FROM (TAB_NAME) INTO <WA>
UP TO anzahl ROWS.
ASSIGN COMPONENT TAB_COMP OF STRUCTURE <WA> TO <COMP>.
WRITE: / TAB_COMP, <COMP>.
ENDSELECT.
In der Anweisung
Ist der Typ von feld oder von <f> eine tiefe Struktur, dann wurde außerdem geprüft, ob alle referenzartigen Komponenten bezüglich Offset und Typ im Bereich von feld, der durch <f> überdeckt wird, übereinstimmen. Die Prüfung der referenzartigen Komponenten wird im Syntaxcheck dahingehend verschärft, daß diese auf allen Plattformen mit ein, zwei oder vier Byte langen Zeichen passen müssen. Zur Laufzeit wird wiederum nur geprüft, ob die Referenzkomponenten im aktuellen System passen.
Bei
ASSIGN str TO <f> TYPE C/N und bei ASSIGN str TO <f> CASTING TYPE C/N kann in Unicode-Systemen außerdem der Fall auftreten, daß die Länge von str nicht ein Vielfaches der Zeichenlänge ist. In diesem Fall erfolgt ein Laufzeitabbruch.
Im Zusammenhang mit
Strukturerweiterungen sind die im Dictionary verwendeten Kategorien zu beachten.