Concepts / Conditional Logic and Decision Making

Conditional Logic and Decision Making

The Guardian Pattern strategically places a guard condition before a risky operation in an 'and' expression to prevent runtime errors.

  • Programming

Why Order Matters

A logical expression can do more than produce a final true or false result. The order of its conditions can determine whether a later operation runs at all. The Guardian Pattern takes advantage of this behavior by placing a safe guard condition before an operation that could cause a runtime error.

What do you think happens?

Suppose an and expression checks a guard first, and that guard is false. What happens to the risky operation that comes after it?

  • The risky operation runs first
  • The risky operation is skipped
  • Both operations always run
  • The guard is ignored
Reveal answer

Answer: The risky operation is skipped

Short-circuit evaluation stops the expression as soon as a condition is false, so subsequent operations do not run.

Following a Guarded Expression

The Guardian Pattern has two parts. First comes the guard: a condition that checks whether it is safe to continue. After the guard comes the risky operation: an operation that should run only when the guard succeeds. In an and expression, a false guard stops evaluation before the risky operation is reached.

evaluates falseshort-circuitevaluates truecontinueGuard conditionfirst checkFalseExpression stopsrisky operation skippedTrueRisky operationevaluated only after theguard succeeds
What happens next when the guard is false, and why is the risky operation never evaluated?

Checking a Denominator Before a Calculation

A calculation should use a denominator only when the denominator is non-zero. Which condition must come first in the guarded and expression?

Identify the guard: The non-zero check is the guard because it determines whether the denominator is safe to use.

Identify the risky operation: The calculation using the denominator is the risky operation because it should not run when the denominator is zero.

Order the conditions: Place the non-zero guard before the calculation in the and expression.

Apply short-circuit evaluation: When the guard is false, the expression stops and the calculation is not evaluated.

The non-zero denominator check protects the calculation only when it appears before the calculation.

Building the Safe Order

To construct a guarded and expression, first identify what could cause a runtime error. Then identify the condition that proves the operation is safe. Place that guard before the risky operation. The guard must be evaluated early enough to stop the expression before the risky operation is reached.

guard succeedsGuard conditionevaluated firstRisky operationevaluated only if safe
How does placing the safe guard before the risky operation prevent a runtime error?
Potentially risky useGuard to place first
Using a denominator in a calculationCheck that the denominator is non-zero
Using an array indexCheck that the index is valid
Using a data valueCheck that the data value is valid

Common guard-and-operation relationships

When Protection Fails

An incorrectly ordered expression evaluates the risky operation before it reaches the guard. If that operation encounters an unsafe value, the runtime error can occur before the guard has any chance to stop evaluation. The same guard may be present, but its position makes it ineffective.

guard succeedsoperation evaluated firstGuard firstrisky operation protectedRisky operation firstruns before protectionRisky operationreached only when safeGuard secondmay be reached too late
What changes when the risky operation is evaluated before the guard, and how can that cause an error?
  • Putting the guard after the risky operation

    Short-circuit evaluation can stop only operations that have not yet been reached. It cannot undo an operation that already ran.

    Fix: Move the safety check before the calculation.

  • Treating the presence of a guard as enough

    The guard does not protect an earlier operation.

    Fix: Review the evaluation order, not just the conditions that appear in the expression.

  • Ignoring the specific unsafe input

    The risky operation can run with an unsafe denominator before any protection is applied.

    Fix: Match the guard to the risk and place the non-zero check first.

Guard Construction Practice

EASY

For each situation, identify the guard and the risky operation. Then state which one must appear first in an and expression: a denominator that must not be zero, an array index that must be valid, and a data value that must be valid.

Hints
  • The guard states the condition that makes the later operation safe.
  • The risky operation is the use of the value, index, or denominator.
  • The guard must come first so a false result can stop evaluation.
  1. Name the operation that could produce a runtime error.
  2. State the condition that makes that operation safe.
  3. Place the guard before the risky operation in the and expression.
  4. Check the false-guard path: the expression should stop before the risky operation runs.
  5. Check the true-guard path: the expression may continue to the risky operation.

Key Takeaways

  1. The Guardian Pattern places a guard condition before a risky operation in an and expression.
  2. Short-circuit evaluation stops the expression when a condition is false.
  3. A guard can prevent a later operation from running only when the guard comes first.
  4. Common guards check denominators, array indices, and data values before those values are used.
  5. Incorrect ordering can allow a runtime error before the guard is evaluated.

Key Takeaways

  • Use a guard condition to establish that a risky operation is safe.
  • Place the guard before the risky operation in an and expression.
  • Rely on short-circuit evaluation to stop when the guard is false.
  • Remember that a guard placed after the risky operation cannot protect it.