DEV Community

Cover image for Zig vs Go: condition flows
Paolo Carraro
Paolo Carraro

Posted on

Zig vs Go: condition flows

(you can find previous post about same topic here)

Comparing the flow control capabilities between Zig and Go reveals how Zig manages to have a more expressive syntax to solve certain specific cases in a clear and elegant way: for example the labeled block returns a value as a constant that is actually calculated using logic and variables from the scope in which it is defined.
It's also worth noting that Zig's switch must always be exhaustive and therefore not leave any unresolved branches.

// Zig
const std = @import("std");
const random = std.Random;

pub fn main() !void {
    const seed = std.time.timestamp();
    var rpcg = random.DefaultPrng.init(@intCast(seed));
    // calc random integer on range 0 - 10
    const rndInt = random.uintLessThan(rpcg.random(), u8, 10);
    // classic if
    if (rndInt < 5) {
        std.debug.print("number is smaller than 5: {d}\n", .{rndInt});
    } else {
        std.debug.print("number is greater than 4: {d}\n", .{rndInt});
    }
    // if inline
    const result = if (rndInt < 5) "smaller than 5" else "greater than 4";
    std.debug.print("{s}\n", .{result});

    // switch with ranges and lists
    switch (rndInt) {
        0...4 => std.debug.print("number is smaller than 5: {d}\n", .{rndInt}),
        5, 10 => std.debug.print("number is divisible by 5: {d}\n", .{rndInt}),
        6...9 => std.debug.print("number is greater than 4: {d}\n", .{rndInt}),
        else => std.debug.print("number is out of range: {d}\n", .{rndInt}),
    }

    // arbitrary logic: demonstrating how to resolve a value using a labeled block
    const calculatedValue: i16 = lb: {
        if (rndInt == 0) {
            break :lb -300;
        }

        if (rndInt == 3) {
            break :lb -900;
        }
        break :lb rndInt * 5;
    };

    std.debug.print("calculated value based on random init with labeled block: {d}", .{calculatedValue});
}

Enter fullscreen mode Exit fullscreen mode

In Go we can solve the same logic in these two ways

// Go
package main

import (
    "fmt"
    "math/rand"
)

func main() {
    rndInt := rand.Intn(10)

    // classic if
    if rndInt < 5 {
        fmt.Printf("number is smaller than 5: %d\n", rndInt)
    } else {
        fmt.Printf("number is greater than 4: %d\n", rndInt)
    }

    // switch with conditional cases
    switch {
    case rndInt < 5:
        fmt.Printf("number is smaller than 5: %d\n", rndInt)
    case rndInt == 5 || rndInt == 10:
        fmt.Printf("number is divisible by 5: %d\n", rndInt)
    case rndInt > 5:
        fmt.Printf("number is greater than 4: %d\n", rndInt)
    default:
        fmt.Printf("number is out of range: %d\n", rndInt)
    }
}
Enter fullscreen mode Exit fullscreen mode

Top comments (0)