Chapter 28: Swift Operator Precedence
1. What is Operator Precedence?
When you write an expression with multiple operators, Swift has to decide which one to do first.
Operator precedence = the set of rules that decides the order of operations.
Example most people recognize from school math:
|
0 1 2 3 4 5 6 |
2 + 3 * 4 |
What’s the result?
- If we do left-to-right: 2 + 3 = 5 → 5 * 4 = 20
- But the correct answer is 14 — because multiplication has higher precedence than addition
Swift follows very similar rules to math, but with more operators and some Swift-specific twists.
2. The Most Important Precedence Levels (the ones you meet every day)
Here are the precedence groups you will actually use — ordered from highest to lowest:
| Priority | Operators | Meaning / Category | Associativity | Example | Result |
|---|---|---|---|---|---|
| Highest | ! ~ (unary minus, logical NOT, bitwise NOT) | Unary operators | Right | -5 + 3 | -2 |
| Very high | * / % &* &/ &% | Multiplication, division, remainder | Left | 10 + 6 * 2 | 22 |
| High | + – &+ &- | Addition, subtraction | Left | 2 + 3 * 4 | 14 |
| Medium | ..< … | Range operators | — | 1…5 | — |
| Medium | < <= > >= is as? as! | Comparison & type casting | — | age > 18 && hasLicense | — |
| Low | == != === !== ~= | Equality & identity | — | a == b && c != d | — |
| Lower | && | Logical AND | Left | true && false |
|
| Lowest | |
Logical OR | Left | ||
| Very low | ?? | Nil-coalescing | Right | a ?? b ?? c | — |
| Lowest | =, +=, -=, *=, /=, %=, … | Assignment operators | Right | a = b + c | — |
Key rules to remember:
- Higher precedence operators are evaluated first
- When precedence is the same → left-to-right (except assignment and ?? which are right-to-left)
- You can always force order using parentheses ()
3. Step-by-step examples – let’s calculate together
Example 1 – Classic math confusion
|
0 1 2 3 4 5 6 7 8 9 10 11 |
let result = 10 + 5 * 2 print(result) // 20 // Why not 30? // * has higher precedence than + // so it's: 10 + (5 * 2) = 10 + 10 = 20 |
Correct way if you want 30:
|
0 1 2 3 4 5 6 |
let result2 = (10 + 5) * 2 // 30 |
Example 2 – Logical operators + comparison
|
0 1 2 3 4 5 6 7 8 9 10 11 12 |
let age = 17 let hasConsent = true let isRestricted = false let canWatch = age >= 18 || hasConsent && !isRestricted print(canWatch) // true |
What actually happens?
Because && has higher precedence than ||, it is evaluated first:
|
0 1 2 3 4 5 6 7 |
// Equivalent to: let canWatch = age >= 18 || (hasConsent && !isRestricted) |
So:
- hasConsent && !isRestricted → true && true → true
- age >= 18 → false
- false || true → true
If you wanted different grouping, use parentheses:
|
0 1 2 3 4 5 6 |
let canWatchStrict = (age >= 18 || hasConsent) && !isRestricted |
Example 3 – Assignment & arithmetic
|
0 1 2 3 4 5 6 7 8 9 10 11 |
var total = 100 total += 20 * 3 // what happens? // * has higher precedence than += // so: 20 * 3 = 60 // then total += 60 → total = 160 |
If you wanted something else:
|
0 1 2 3 4 5 6 7 |
total += 20 // first total *= 3 // then |
4. Very Common Real-Life Examples
Example 1 – Discount & tax calculation
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
let price = 999.99 let discountPercent = 15.0 let taxRate = 0.18 let finalPrice = price * (1 - discountPercent / 100) * (1 + taxRate) // What happens? // / and * have same precedence → left to right // discountPercent / 100 → 0.15 // 1 - 0.15 → 0.85 // price * 0.85 → 849.9915 // 849.9915 * 1.18 → ~1002.99 |
Safer & clearer with parentheses:
|
0 1 2 3 4 5 6 7 |
let discounted = price * (1 - discountPercent / 100) let finalPrice = discounted * (1 + taxRate) |
Example 2 – Form validation (very common)
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
let email = "test@example.com" let password = "Pass123!" let isValid = email.contains("@") && email.contains(".") && password.count >= 8 && password != "password" print(isValid) // true |
Here && chains are evaluated left to right — if any condition fails, the rest are skipped (short-circuit).
5. The Most Dangerous Beginner Mistake
Forgetting precedence between && and ||
|
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
let a = false let b = true let c = true let result = a || b && c // What people often think: (false || true) && true = true && true = true // What actually happens: false || (true && true) = false || true = true // But many beginners expect different grouping |
Always use parentheses when mixing && and ||
|
0 1 2 3 4 5 6 |
let result = (a || b) && c // now very clear |
6. Quick Reference – Precedence Summary (the operators you use most)
| Priority | Operators you meet often | Evaluated first? | Left-to-right or right-to-left? |
|---|---|---|---|
| Highest | ! - (unary) | Yes | Right-to-left |
| High | * / % | Yes | Left-to-right |
| Medium | + - | — | Left-to-right |
| Medium | > < >= <= == != | — | — |
| Low | && | — | Left-to-right |
| Lowest | ` | ||
| Lowest | ?? | — | Right-to-left |
| Lowest | = += -= *= /= %= | — | Right-to-left |
7. Golden Rules for Writing Safe & Readable Code
- When in doubt → use parentheses(a + b) * c is clearer than a + b * c
- Never rely on precedence when mixing && and || Always group with ()
- Short conditions are usually clearer than one giant expression
Bad:
|
0 1 2 3 4 5 6 |
if age >= 18 && hasLicense && !isSuspended && hasInsurance && carIsRegistered { … } |
Better:
|
0 1 2 3 4 5 6 7 8 9 |
let canDrive = age >= 18 let hasAllDocuments = hasLicense && !isSuspended && hasInsurance && carIsRegistered if canDrive && hasAllDocuments { … } |
8. Small Practice – Predict the result
Try to guess before running:
|
0 1 2 3 4 5 6 7 8 9 10 11 |
print(5 + 3 * 4) // ? print( (5 + 3) * 4 ) // ? print(10 - 4 / 2) // ? print(10 - 4 / 2.0) // ? print(true || false && true) // ? print( (true || false) && true) // ? |
What would you like to explore next?
- More complex expressions with && / || / ?? / ranges
- Operator precedence in switch and guard statements
- How precedence interacts with optional chaining and nil-coalescing
- Writing readable conditions in real forms / validation
- Or move to another topic (control flow, functions, optionals…)
Just tell me — we’ll keep going in the same patient, detailed, teacher-like style 😊
