Control statements decide which branch of logic gets executed. This chapter covers classical IF/CASE alongside the modern functional operators COND and SWITCH, which let you assign a value conditionally in a single expression.
CASE ls_order-order_type.
WHEN 'ZSTD'.
WHEN 'ZRET'.
WHEN OTHERS.
ENDCASE.CHECK <cond> leaves the entire current processing block when the condition is false. Inside a LOOP it skips to the next iteration; inside a method, FORM or event block it exits that block entirely.
" Inside a loop: skip rows that already have an error
LOOP AT lt_items INTO DATA(ls_item).
CHECK NOT line_exists( lt_return[ item = ls_item-posnr type = 'E' ] ).
process_item( ls_item ).
ENDLOOP.
⚠️ CHECKis not a general-purpose guard, and its polarity catches people out. Because it exits when the condition is false, a statement such asCHECK sy-subrc <> 0.continues only on the error path and abandons the block on success — usually the exact opposite of the author's intent. UseIFwhen you want to branch, and keepCHECKfor genuinely skipping the current loop pass.
Classic IF/ELSE still has its place, but for assigning a value based on a condition, the functional COND #( ) operator is more concise and avoids intermediate variables:
DATA lv_begin_date TYPE d VALUE '20200505'.
DATA lv_end_date TYPE d VALUE '20200515'.
" State the result type explicitly when the branches are literals
DATA(lv_status) = COND char10( WHEN sy-datum < lv_begin_date THEN 'EARLY'
WHEN sy-datum > lv_end_date THEN 'LATE'
ELSE 'OK' ).
" '#' is fine when the type is clearly derivable from the operands
DATA(lv_flag) = COND #( WHEN lv_warehouse = lc_warehouse
THEN lc_indicator
ELSE space ).
DATA(lv_in_range) = COND abap_bool( WHEN lv_confirmation_no BETWEEN 50 AND 100
THEN abap_true
ELSE abap_false ).
DATA(lv_plant_code) = COND char3( WHEN is_defect->plant = '1000' THEN 'ONE'
WHEN is_defect->plant = '1100' THEN 'TWO'
WHEN is_defect->plant = '1200' THEN 'THR'
ELSE '' ).
⚠️ Know what#resolves to. When the operand type cannot be derived from the position — as in an inline declaration — the ABAP documentation states that the type is taken from the operand after the firstTHEN. SoDATA(lv_status) = COND #( ... THEN 'EARLY' ... ELSE 'OK' )compiles, butlv_statusbecomesc LENGTH 5, and a longer branch added later would be silently truncated. Write the type explicitly whenever the branches are literals.
SWITCH is the functional equivalent of CASE, useful for assigning a value based on a single variable's content:
DATA(lv_status) = SWITCH char10( sy-msgty
WHEN 'S' THEN 'SUCCESS'
WHEN 'W' THEN 'OK'
WHEN 'E' THEN 'ERROR'
ELSE 'UNKNOWN' ).| Construct | Best For | Returns a Value? |
|---|---|---|
IF / ELSEIF / ELSE |
Multiple, unrelated conditions; executing statements | ❌ No |
CASE |
Branching on one variable's exact value; executing statements | ❌ No |
COND #( ) |
Assigning a value based on one or more conditions | ✅ Yes |
SWITCH #( ) |
Assigning a value based on one variable's value | ✅ Yes |
- Use
COND/SWITCHwhen the goal is to compute a value — they remove boilerplateIF/ELSEblocks that repeat the same assignment target. - Use
CASE/IFwhen the goal is to execute different logic, not just assign a value. - Always include an
ELSE/WHEN OTHERSbranch, especially in status mapping. - State the result type explicitly (
COND char10( ... ),SWITCH string( ... )) whenever the branches are literals —#will derive a type from the firstTHEN, and it may not be the one you want.
- Using
COND/SWITCHfor complex multi-statement branches — they are expressions, not substitutes for fullIFblocks. - Relying on
#and getting a narrower type than intended, so later branches are silently truncated. - Forgetting that
CONDwithout anELSEreturns the type's initial value when nothing matches, hiding the "no match" case. - Getting
CHECK's polarity backwards, so the block is abandoned on the success path. - Overusing
CHECKdeep inside nested loops — prefer an explicitIF ... CONTINUE/EXIT.
- Be ready to rewrite a nested
IF/ELSEIFchain as aCONDexpression, and explain the trade-offs. - Explain how
#resolves for a constructor expression, and when you must give the type explicitly. - Explain what happens when
CHECKevaluates to false inside aLOOPvs. inside a method or event block.
- 04-Operators
- 06-Loops
- 07-Internal-Tables —
CONDinsideVALUE/REDUCEexpressions