Swift重复URLSession创建大量内存泄漏

时间:2017-03-28 16:06:04

标签: swift xcode memory-management memory-leaks nsurl

我有一个应用程序(部分)显示用户的Wi-Fi连接的当前下载速度。它通过打开URLSession并下载中等大小(~10MB)文件并测量所花费的时间来实现。

这是URLSession函数:

func testSpeed() {

    Globals.shared.dlStartTime = Date()
    Globals.shared.DownComplete = false

    if Globals.shared.currentSSID == "" {
        Globals.shared.bandwidth = 0
        Globals.shared.DownComplete = true
    } else {

        let url = URL(string: [HIDDEN])
        let session = URLSession(configuration: URLSessionConfiguration.default, delegate: self, delegateQueue: nil)
        let task = session.downloadTask(with: url!)

        task.resume()
    }
}

public func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didWriteData bytesWritten: Int64, totalBytesWritten: Int64, totalBytesExpectedToWrite: Int64) {


    Globals.shared.dlFileSize = (Double(totalBytesExpectedToWrite) * 8) / 1000
    let progress = (Double(totalBytesWritten) / Double(totalBytesExpectedToWrite)) * 100.0

    NotificationCenter.default.post(name: NSNotification.Name(rawValue: "ProcessUpdating"), object: nil, userInfo: ["progress" : progress])
}

public func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didFinishDownloadingTo location: URL) {
    let elapsed = Double( Date().timeIntervalSince(Globals.shared.dlStartTime))
    Globals.shared.bandwidth = Int(Globals.shared.dlFileSize / elapsed)
    Globals.shared.DownComplete = true
    Globals.shared.dataUse! += (Globals.shared.dlFileSize! / 8000)
    session.invalidateAndCancel()

    NotificationCenter.default.post(name: NSNotification.Name(rawValue: "ProcessFinished"), object: nil, userInfo: nil)
}

正如您可以通过委托函数所知,这一切都存在于视图控制器的单独类中,以及其他一些小型网络功能,如获取IP和SSID。代表发布视图控制器观察到的通知。

我的ViewController有一个NSTimer,它每5秒回调一次这个URLSession以重新测试速度(但只有在前一个完成时才运行它)。这是代码:

reloadTimer = Timer.scheduledTimer(timeInterval: 5.0, target: self, selector: #selector(rescanNetwork), userInfo: nil, repeats: true)

调用此功能:

func backgroundRescan() {
    if Globals.shared.DownComplete {
        Networking().testSpeed()
    }
}

再次运行URL会话,当然要检查以确保先前已完成。

出于某种原因,我在测试中会大量增加内存使用量,直到应用程序达到2GB的内存使用量并被控制台输出Message from debugger: Terminated due to memory issue终止。这一切都发生在运行应用程序的两分钟内。

我甚至将session.invalidateAndCancel()添加到完成委托中,以绝望的方式清除内存。但它没有用。我错过了什么吗?

1 个答案:

答案 0 :(得分:2)

正如Rob所说,将URLSessionConfiguration.default作为类中的变量并使用它。 我遇到了同样的问题,最后通过使用包含所有通信方法的singelton类并将URLSessionConfiguration.default设置为成员变量来解决它。我的所有内存泄漏都得到了解决。