当我不需要停止时 time.Tick 会导致内存泄漏吗?

sgo*_*n00 4 go

考虑以下代码:

go func() {
    for now := range time.Tick(time.Minute) {
        fmt.Println(now, statusUpdate())
    }
}()
Run Code Online (Sandbox Code Playgroud)

我需要 for 循环永远运行并且永远不需要停止它。这是否会导致内存泄漏?

我知道如果我需要打破 for 循环,就会导致内存泄漏。但是如果我不需要打破 for 循环怎么办?

医生说

虽然 Tick 对于不需要关闭 Ticker 的客户端很有用,但请注意,如果没有办法关闭它,底层 Ticker 就无法被垃圾收集器恢复;它“泄漏”。

我只是想把事情做好。

Hym*_*sco 7

首先,让我们看看维基百科对“内存泄漏”的定义:

在计算机科学中,内存泄漏是一种资源泄漏,当计算机程序错误地管理内存分配,导致不再需要的内存未被释放时,就会发生这种情况。

需要注意的是,在您引用的文档中,它没有具体提到“内存泄漏”,只是“泄漏”(意思是“资源泄漏”)。所讨论的资源不仅是代码使用的内存,还包括运行它的 goroutine。因此,我将把这个定义解释为更广泛地适用于“资源泄漏”。

正如您引用的文档所提到的,time.Tick无法释放股票的资源。

因此,根据这个定义,如果程序中的任何后续点不再需要该代码,则发生资源泄漏。如果创建后程序的其余部分始终需要代码,那么这不是泄漏。

然而,在维基百科的定义中,还有这样的注释:

当对象存储在内存中但无法被运行的代码访问时,也可能会发生内存泄漏。

同样,time.Tick也无法释放股票代码的资源。

因此,根据这个连续的定义,您可能会说使用time.Tick始终是资源泄漏。

实际上,只要您range完成了time.Tickwithout breaking,您就有合理的保证该股票代码将继续用于程序的其余部分,并且不会出现“泄漏”。如果您对股票代码是否会永远使用有任何疑问,请适当time.NewTicker使用:Stop()

go func() {
    ticker := time.NewTicker(time.Minute)
    defer ticker.Stop()

    for now := range ticker.C {
        fmt.Println(now, statusUpdate())
        // some exception
        if (something) {
            break
        }
    }
}()
Run Code Online (Sandbox Code Playgroud)