📜  Golang 中的恐慌

📅  最后修改于: 2021-10-25 02:09:57             🧑  作者: Mango

在 Go 语言中,panic 就像一个异常,它也是在运行时出现的。或者换句话说,panic 意味着在你的 Go 程序中出现意外情况,导致程序的执行被终止。有时会在运行时发生恐慌,因为某些特定情况出现,例如越界数组访问等,如示例 1 所示,或者有时是程序员故意抛出以在 Go 程序的帮助下处理最坏情况的情况panic()函数如例 2 所示。
panic函数是一个内置函数,定义在 Go 语言的 builtin 包下。此函数终止控制流并开始恐慌。

句法:

func panic(v interface{})

它可以接收任何类型的参数。当 Go 程序发生恐慌时,程序在运行时终止,并在输出屏幕中显示一条错误消息以及直到发生恐慌的点的堆栈跟踪。通常,在 Go 语言中,当程序发生恐慌时,程序不会立即终止,而是在 go 完成该程序的所有未决工作时终止。
例如,假设一个函数的调用恐慌,那么函数A的执行被停止,如果任何延迟功能于一身可用,那么他们是执行正常后,该函数的返回调用者和调用者的行为像呼吁恐慌。这个过程一直持续到当前 goroutine 中的所有函数都返回,然后程序崩溃,如示例 3 所示。

示例 1:

// Simple Go program which illustrates
// the concept of panic
package main
  
import "fmt"
  
// Main function
func main() {
  
    // Creating an array of string type
    // Using var keyword
    var myarr [3]string
  
    // Elements are assigned
    // using an index
    myarr[0] = "GFG"
    myarr[1] = "GeeksforGeeks"
    myarr[2] = "Geek"
  
    // Accessing the elements
    // of the array
    // Using index value
    fmt.Println("Elements of Array:")
    fmt.Println("Element 1: ", myarr[0])
  
    // Program panics because
    // the size of the array is
    // 3 and we try to access
    // index 5 which is not 
    // available in the current array,
    // So, it gives an runtime error
    fmt.Println("Element 2: ", myarr[5])
  
}

输出:

./prog.go:32:34: invalid array index 5 (out of bounds for 3-element array)

示例 2:

// Go program which illustrates 
// how to create your own panic
// Using panic function
package main
  
import "fmt"
  
// Function
func entry(lang *string, aname *string) {
  
    // When the value of lang 
    // is nil it will panic
    if lang == nil {
        panic("Error: Language cannot be nil")
    }
      
    // When the value of aname
    // is nil it will panic
    if aname == nil {
        panic("Error: Author name cannot be nil")
    }
  
    // When the values of the lang and aname 
    // are non-nil values it will print 
    // normal output
    fmt.Printf("Author Language: %s \n Author Name: %s\n", *lang, *aname)
}
  
// Main function
func main() {
  
    A_lang := "GO Language"
  
    // Here in entry function, we pass 
    // a non-nil and nil values
    // Due to nil value this method panics
    entry(&A_lang, nil)
}

输出:

panic: Error: Author name cannot be nil

goroutine 1 [running]:
main.entry(0x41a788, 0x0)
    /tmp/sandbox108627012/prog.go:20 +0x140
main.main()
    /tmp/sandbox108627012/prog.go:37 +0x40

示例 3:

// Go program which illustrates the
// concept of Defer while panicking
package main
  
import (
    "fmt"
)
  
// Function
func entry(lang *string, aname *string) {
  
    // Defer statement
    defer fmt.Println("Defer statement in the entry function")
  
    // When the value of lang
    // is nil it will panic
    if lang == nil {
        panic("Error: Language cannot be nil")
    }
      
    // When the value of aname
    // is nil it will panic
    if aname == nil {
        panic("Error: Author name cannot be nil")
    }
  
    // When the values of the lang and aname
    // are non-nil values it will 
    // print normal output
    fmt.Printf("Author Language: %s \n Author Name: %s\n", *lang, *aname)
}
  
// Main function
func main() {
  
    A_lang := "GO Language"
  
    // Defer statement
    defer fmt.Println("Defer statement in the Main function")
  
    // Here in entry function, we pass
    // one non-nil and one-nil value
    // Due to nil value this method panics
    entry(&A_lang, nil)
}

输出:

Defer statement in the entry function
Defer statement in the Main function
panic: Error: Author name cannot be nil

goroutine 1 [running]:
main.entry(0x41a780, 0x0)
    /tmp/sandbox121565297/prog.go:24 +0x220
main.main()
    /tmp/sandbox121565297/prog.go:44 +0xa0

注意: Defer 语句或函数始终运行,即使程序出现混乱。

恐慌的用法:

  • 对于程序无法继续执行的不可恢复错误,您可以使用 panic。
  • 如果您希望程序中的特定条件出错,您也可以使用 panic。