Golang Backend Real-World (Part 4): Control Flow (if, for, switch, defer)

Golang Backend Real-World (Part 4): Control Flow (if, for, switch, defer)
Golang Backend Real-World (Part 4): Control Flow (if, for, switch, defer)

Control Flow in Golang: if, for, switch & defer

Control flow determines how your program makes decisions, handles loops, and controls execution order.
In real backend services—authentication, validation, routing, middleware, DB operations—control flow constructs appear everywhere.

Go keeps these constructs simple, predictable, and highly consistent.


1. if Statements

Go’s if statements do not require parentheses and support an optional initialization statement.


1.1 Basic if usage

age := 20

if age >= 18 {
    fmt.Println("Allowed")
}


1.2 if-else

if age >= 18 {
    fmt.Println("Adult")
} else {
    fmt.Println("Minor")
}


1.3 if with initialization

Very common in backend code (e.g., database or cache lookups):

if user, err := repo.GetUser(id); err == nil {
    fmt.Println("Found:", user.Name)
} else {
    fmt.Println("User not found")
}


2. for Loops

Go has only one loop keyword: for.
It covers classic loops, while-loops, and infinite loops.


2.1 Classic counter loop

for i := 0; i < 5; i++ {
    fmt.Println(i)
}


2.2 Range loop (important for backend models and DTOs)

users := []string{"alice", "bob"}

for index, name := range users {
    fmt.Println(index, name)
}

Used everywhere when iterating JSON payloads, DB results, configs, etc.


2.3 Infinite loop

Used in workers, consumers, schedulers:

for {
    processJob()
}


3. switch Statements

More powerful than other languages — supports conditions, multiple cases, type switches, and more.


3.1 Basic switch

status := 200

switch status {
case 200:
    fmt.Println("OK")
case 400:
    fmt.Println("Bad Request")
default:
    fmt.Println("Unknown")
}


3.2 Multiple matches

switch ext := "jpg"; ext {
case "jpg", "jpeg":
    fmt.Println("Image file")
case "mp4":
    fmt.Println("Video file")
default:
    fmt.Println("Other type")
}


3.3 Type switch

Used for handling interfaces in backend systems.

func printType(v interface{}) {
    switch v.(type) {
    case int:
        fmt.Println("Integer")
    case string:
        fmt.Println("String")
    default:
        fmt.Println("Unknown")
    }
}


4. defer

defer schedules a function to run after the current function finishes, similar to a “finally” block.

Used extensively in backend systems for:

  • closing DB connections
  • releasing locks
  • closing file handles
  • logging

4.1 Basic example

func readFile() {
    f, _ := os.Open("data.txt")
    defer f.Close()  // always runs at the end

    fmt.Println("Reading file...")
}


4.2 Multiple defers execute LIFO

defer fmt.Println("first")
defer fmt.Println("second")

Output:

second
first


5. Summary

In Part 4, you learned how Golang handles control flow using:

if and if with initialization
✔ All versions of for loops
switch for values and types
defer for resource cleanup

These constructs appear constantly in production backend development.

About Leaf 51 Articles
"Thành công nuôi dưỡng sự hoàn hảo. Sự hoàn hảo lại nuôi lớn thất bại. Chỉ có trí tưởng tượng mới tồn tại."