Goto Statement Usage

GolangGolangBeginner
Practice Now

Introduction

Compared to branch and loop statements, the goto statement is more flexible. We can use goto to perform unconditional jumps within the same function.

While it may reduce the readability of the code, its advantage lies in its flexibility. Correct usage not only improves program efficiency but also makes the code more concise.

In this lab, we will explain the syntax and usage of the goto statement.

Knowledge Points:

  • Usage of goto

Skills Graph

%%%%{init: {'theme':'neutral'}}%%%% flowchart RL go(("`Golang`")) -.-> go/BasicsGroup(["`Basics`"]) go(("`Golang`")) -.-> go/FunctionsandControlFlowGroup(["`Functions and Control Flow`"]) go/BasicsGroup -.-> go/variables("`Variables`") go/FunctionsandControlFlowGroup -.-> go/for("`For`") go/FunctionsandControlFlowGroup -.-> go/functions("`Functions`") subgraph Lab Skills go/variables -.-> lab-149074{{"`Goto Statement Usage`"}} go/for -.-> lab-149074{{"`Goto Statement Usage`"}} go/functions -.-> lab-149074{{"`Goto Statement Usage`"}} end

Syntax of goto

The syntax is as follows:

// Syntax 1
goto label
...
label: code block
// Syntax 2
label: code block
goto label

The syntax of goto is very flexible. You can declare a label before the jump or declare it later.

The label is the jump name we declare. Go is case-sensitive, and it is generally recommended to use uppercase letters for labels to improve code readability.

Note: The label declaration and usage must be in the same function.

Let's look at a simple example. Create a file named goto.go and write the following code:

package main

import "fmt"

func main() {
    fmt.Println(1)
    goto NEXT
    fmt.Println(2)
NEXT:
    fmt.Println(3)
}

The output is as follows:

1
3

We can see that the program skipped 2 and directly output 3.

The actual flow is that after outputting 1, the program jumps to the NEXT label below using goto. Therefore, the middle 2 is ignored.

Replace break with goto

The functionality of goto is flexible enough. We can use it to implement many features. For example, we replaced the break statement in the for loop with goto:

package main

import "fmt"

func main() {
    for i := 0; ; i++ {
        if i == 10 {
            goto END
        }
        fmt.Print(i)
    }
END:
    fmt.Println("END")
}

The output is as follows:

0123456789END

Implement a for loop with goto

We can also use goto to implement a for loop. In the following code, we use goto to output the numbers 0 to 9:

package main

import "fmt"

func main() {
    var i = 0
BEGIN:
    fmt.Printf("%d ", i)
    if i == 9 {
        goto END
    }
    i++
    goto BEGIN
END:
}

The output is as follows:

0 1 2 3 4 5 6 7 8 9

In this program, we used BEGIN and END as two labels. The BEGIN label continuously outputs numbers. If the value of the variable i is equal to 9, it will jump to the END label.

Jump out of nested loops with goto

Goto can not only replace other statements but also simplify the code. Let's take a look at an example:

package main

import "fmt"

func main() {
    // First loop
    for i := 0; i < 5; i++ {
        // Second loop
        for j := 0; j < 5; j++ {
            if j == 3 {
                goto END
            }
            fmt.Println(i, j)
        }
    }
END:
}

In this program, we wrote a nested loop and set it to exit the entire loop when j is 3.

If we use the break statement to implement this program, as shown below:

package main

import "fmt"

func main() {
    // Check variable
    var check = false
    // First loop
    for i := 0; i < 5; i++ {
        // Second loop
        for j := 0; j < 5; j++ {
            if j == 3 {
                // Exit the second loop
                check = true
                break
            }
            fmt.Println(i, j)
        }
        // Determine whether to exit the first loop
        if check == true {
            break
        }
    }
}

Let's compare the programs using break and goto. We can find that the program using goto is more concise and understandable.

The second program uses two break statements and a check variable to exit.

If there are more nested loops, more break statements need to be added at each level of the loop.

Summary

In this lab, we introduced the goto jump statement. Let's review what we have learned today:

  • goto unconditionally jumps to the specified label.
  • It is recommended to use uppercase letters for labels.

The goto statement can achieve unconditional jumps and simplify some process of flow control, such as jumping out of nested loops. However, improper use will increase code confusion and complexity.

In the next experiment, we will enter the world of advanced data structures and learn about structures such as arrays, slices, and maps.

Other Golang Tutorials you may like