以下是Swift中的内存泄漏吗?

时间:2015-08-24 11:44:57

标签: ios swift

这是Swift编程中以下场景中的内存泄漏吗?

var string: String = "test-string-1"  //  statement-1

string = "test-string-2" //  statement-2

从statement-1到statement-2执行内存是否泄漏?

或者我这样做吗?

var string: String? = "test-string-1"

string = nil

string = "test-string-2"

请回答正确的说明。

2 个答案:

答案 0 :(得分:2)

你不需要以第二种方式做。 我想第一种情况足够安全。

将字符串设置为"test-string-2"后,"test-string-1"的引用计数变为0.因此,它将被ARC取消分配。

答案 1 :(得分:1)

这里你甚至不需要考虑内存泄漏,这与为变量赋值有很大不同。当一个实例无法从内存中释放并且由Apple in the docs详细解释时会发生这种情况,但简言之,这是最简单的场景:

$scope.amount = 1234567;

{{amount | number}}

A"强参考周期"已创建,因为父级拥有对子实例的引用,并且该子实例持有对包含对其的引用的父实例的引用。结果是无法确定何时取消初始化任一实例。这可以通过将代码放在视图控制器中并在app中运行来证明:

class Parent {
    var child:Child?
}

class Child {
     var parent: Parent?
}

var child = Child()
let parent = Parent()

child.parent = parent
parent.child = child // strong reference cycle created

请注意,没有控制台消息表明发生了取消初始化,因为它没有。相反,这些实例都永远存在。我们称之为泄漏,因为实例不会存在,但同时它们无法访问。

现在将其中一个引用改为弱,如下所示:

import UIKit

class Parent {
    var child:Child?
    deinit {
        print("deinitialized")
    }
}

class Child {
    var parent: Parent?
    deinit {
        print("deinitialized")
    }
}
class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        let child = Child()
        let parent = Parent()

        child.parent = parent
        parent.child = child // strong reference cycle created
    }

}

你会看到两条deinit消息。单独的父母现在负责让孩子保持活着,因此当孩子通过ARC自动离开时,它可以释放孩子。对于谁拥有谁,即使所拥有的实例提及其所有者,也没有任何歧义,因为它现在很弱(而不是强大)。