猿问

Go中的短路评估

我对短路评估的理解是,仅在 if 语句中需要时才调用表达式。Go 遵循这个吗?


例如,我会从以下方面获得更好的平均表现:


if !isValidQueryParams(&queries) || r == nil || len(queries) == 0 {

    return "", fmt.Errorf("invalid querystring")

}

...对此:


if r == nil || len(queries) == 0 || !isValidQueryParams(&queries) {

    return "", fmt.Errorf("invalid querystring")

}

...因为是一个开销比测试地图长度isValidQueryParams多得多的函数吗?r == nil


即解释器是否会首先评估 r == nil,看到它是真的而不费心去评估其他条件?


编辑:错误地将短路评估称为惰性评估


30秒到达战场
浏览 155回答 3
3回答

慕沐林林

Go 确实实现了正常的短路评估,可以用以下代码推导出:package mainimport "fmt"func main() {    for i := 0; i < 10; i++ {        if testFunc(1) || testFunc(2) {            // do nothing        }    }}func testFunc(i int) bool {    fmt.Printf("function %d called\n", i)    return true}...这将永远给:$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called$ function 1 called

互换的青春

这称为短路评估。根据本教程,布尔运算符使用这个:尽管在Go 语言规范中没有明确说明 Go 使用短路评估,但确实提到了逻辑运算符应用于布尔值并产生与操作数相同类型的结果。有条件地评估右操作数。这是一个简单的例子来证明 Go 使用短路评估[…]

ibeautiful

您所指的是所谓的“短路求值”——也就是说,仅在完整结果可用时才使用正常的关联性规则对子表达式求值,并且对其余表达式的求值不会根据有问题的二元运算符的规则。Go 确实实现了逻辑表达式的短路评估。“惰性求值”完全是另一回事——通常在所谓的“函数式”编程语言中实现,并没有直接在 Go 中实现。话虽如此,我会注意到虽然 Go 没有直接(与语法和运行时一样)支持惰性求值,但可以在需要时使用它。例如,您可能有一个 goroutine 从通道读取可能无限数量的项目,并以一种或另一种方式处理它们,而另一个 goroutine(或其中的几个)产生这些值并通过通道发送它们。这样,这些值只会在接收端“具体化”,不会比它们实际准备好处理的速度更快。
随时随地看视频慕课网APP

相关分类

Go
我要回答