我惊讶地发现这两个程序产生相同的输出:
方案A
package main
import "fmt"
func main() {
defer fmt.Println(1)
defer fmt.Println(2)
} //prints 2 1
方案B
package main
import "fmt"
func main() {
{
defer fmt.Println(1)
}
defer fmt.Println(2)
} //prints 2 1
换句话说,“defer”语句似乎忽略了词法闭包[edit:感谢@ twotwetwo纠正了我的术语,我的意思是说“块”而不是“词法闭包”],并且严格限制在函数的范围内。我想知道:
1.我的理解是否正确?
1.有没有一种方法可以将它的范围限定在块上,这样它就可以在退出闭包时触发,而不是在退出函数时触发?
我可以想象按顺序执行几个工作单元,每个单元都需要在继续之前关闭自己的资源……如果不是为了那个目的而把它们分解成单独的函数就好了。
2条答案
按热度按时间vc9ivgsu1#
1.我的理解是否正确?
是的
1.有没有办法把它的范围扩大到块[...]?
没有办法改变
defer
的工作方式。根据您试图解决的问题,拆分函数(example)或定义匿名函数(example)可能会有所帮助。后者仅供参考,可能最好避免,因为它使代码可读性降低。更多关于
defer
的信息,请访问Go Spec.ttvkxqim2#
是否正确?
是的
为什么?
如果你只能有一个行为,功能与块,哪一个更容易定义另一个?
defer
在块上工作。如果你想在更大的范围内,你不能。有时候,Go需要你输入一个新的块,就像在if
语句中一样,这使得在应用defer时很难控制。defer
的作用域是函数,那么您可以轻松地添加一个新函数来缩小作用域。你甚至可以有一个你直接调用的匿名函数。