我正在尝试从3台服务器下载内容。我的想法是,如果第一台服务器关闭,它将使用第二台服务器。我注意到,如果第一台服务器已经关闭,它会产生一个运行时错误。我想知道如何使用这个错误,我需要的是这样的:
if run time err!=nil{do something}
我是golang的新手,希望有人可以帮助我 谢谢
答案 0 :(得分:8)
详细说明FUZxxl解释的内容,go区分错误(可能出错的东西确实出错)和异常(不可能的东西)出问题实际上出错了。)
区别有时可能是微妙的(因为它依赖于'意外'),但它也可以比你在其他语言中看到的“一切都是例外”更清晰。
例如,考虑可能溢出的整数。一种可能性是将其视为“正常”行为,应该妥善处理:
func safe_add(x, y uint32) (uint32, error) {
z := x + y
if z < x || z < y {
return 0, fmt.Errorf("Integer overflow")
}
return z, nil
}
另一个是考虑它“永远不会发生”,并且在不太可能的情况下运行panic
时会遇到所有可能性:
func panic_add(x, y uint32) uint32 {
z, err := safe_add(x, y)
if err != nil {
panic(err)
}
return z
}
(请注意,我在这里使用我自己的'safe_add',但你当然不必使用)
主要区别在于您之后处理错误的方式。添加一个数字直到它溢出error
s给出:
func safeloop(u uint32) {
var err error
for {
if u, err = safe_add(u, u); err != nil {
fmt.Println(err)
return
} else {
fmt.Println(u)
}
}
}
处理恐慌时使用recover
内置函数:
func panicloop(u uint32) {
defer func() {
if err := recover(); err != nil {
fmt.Println(err)
}
}()
for {
u = panic_add(u, u)
fmt.Println(u)
}
}
(the playground上的完整示例)
请注意,恐慌版本有一个更简单的循环,因为你基本上从不指望出现任何问题,也从不检查错误。与此相对应的是,处理恐慌的方式非常麻烦,即使对于这样一个非常简单的例子也是如此。您defer
一个函数将调用recover
并在错误发生时捕获错误并突破该函数。当您的代码变得更加复杂时,准确地跟踪恐慌发生的位置和方式并相应地采取行动会比使用result, err := func_which_may_fail(...)
检查可能出现的地方的错误更加复杂 更复杂图案。
你甚至可以在恐慌之间交替,恢复哪些返回错误,错误转换为恐慌,......但这(可以理解)被认为是糟糕的设计。
在博客上的error handling和panics上有一些很好的资源。 specs是一本很好的读物。
在您的情况下,正如您所期望的那样“服务器已关闭”是一种非常频繁的行为,您应该像{1}}那样采用FUZxxl建议的方式,但我希望这对您有用(或者其他)了解错误处理在Go中的工作原理。