mirror of
https://github.com/microsoft/BCQuality.git
synced 2026-10-07 15:46:55 +01:00
Follow-up from PR review: nested if is the right answer for two or three dependent conditions, but past that the nesting becomes the problem. AL's case statement is the flat alternative — the control statements documentation states a value set "must be an expression or a range" and that the first matching value set executes, so case true of / case false of accept boolean expressions and stop at the first match. That is the laziness the boolean operators do not provide. Adds case-true-of-for-long-condition-chains.md with good/bad AL companions: case false of for guard chains where every condition must hold, case true of for first-match dispatch. The bad sample shows both failure shapes — a five-level if ladder, and the worse escape of collapsing it into an and chain, which trades nesting for a real defect. Cross-links both articles, and adds the threshold to the short-circuit article's Best Practice so following it does not lead to a deep ladder. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
30 lines
2.5 KiB
Markdown
30 lines
2.5 KiB
Markdown
---
|
|
bc-version: [all]
|
|
domain: performance
|
|
keywords: [case-statement, case-true-of, nested-if, condition-chain, guard, lazy-evaluation, nesting-depth]
|
|
technologies: [al]
|
|
countries: [w1]
|
|
application-area: [all]
|
|
---
|
|
|
|
# Use case true of for long chains of dependent conditions
|
|
|
|
## Description
|
|
|
|
Because AL gives no short-circuit guarantee for `and` and `or`, a chain of conditions that must be evaluated in order has to be sequenced with nested `if` statements — and past three conditions the nesting itself becomes the problem: the body drifts right, the order of evaluation is carried by indentation alone, and any shared failure path is repeated at every level. AL's `case` statement is the flat alternative. Its value sets "must be an expression or a range", so `case true of` and `case false of` accept arbitrary boolean expressions, and the statement "is evaluated, and the first matching value set executes the associated statement" — evaluation stops at the first match, which is exactly the laziness the boolean operators do not provide.
|
|
|
|
## Best Practice
|
|
|
|
Sequence two or three dependent conditions with nested `if`. Beyond that, switch to `case`: use `case false of` for a chain of guards where every condition must hold, listing the failure action per condition and letting control fall past `end` when all pass; use `case true of` for first-match dispatch, where each later probe runs only if the earlier ones did not match. This keeps every condition at one indentation level, makes evaluation order explicit rather than implied by nesting, and preserves the stop-at-first-match behaviour. It also aligns with the AL programming convention that more than two alternatives belong in a `case` statement rather than an `if-then-else`.
|
|
|
|
See sample: `case-true-of-for-long-condition-chains.good.al`.
|
|
|
|
## Anti Pattern
|
|
|
|
An `if` ladder four or more levels deep whose only purpose is sequencing guards. Detection: a chain of nested `if` statements with no `else`, each condition guarding the one below it, terminating in a single action or `exit`; or the same `exit`/`error` duplicated at every level of such a chain. The second, worse form is collapsing that ladder into one `and` chain to escape the nesting — that trades indentation for a real defect, because the operands are still all evaluated. Reach for `case` instead of either.
|
|
|
|
See sample: `case-true-of-for-long-condition-chains.bad.al`.
|
|
|
|
## See also
|
|
|
|
`boolean-operators-do-not-short-circuit.md` covers the underlying evaluation rule that makes the sequencing necessary in the first place.
|