Избегайте сохранения циклов для указателей на функции в Swift - PullRequest
0 голосов
/ 28 мая 2019

Давайте начнем с этого примера игровой площадки

Пример 1

import UIKit

internal final class TestClass1 {
    var testVar: Int = 1

    internal init() {
        print("TestClass1 init is called!")
    }

    deinit {
        print("TestClass1 deinit is called!")
    }

    internal func func1() {
        print("func1 is called!")
    }
}

internal final class TestClass2 {
    init() {
        let testClass1: TestClass1 = TestClass1()
        testClass1.testVar = 10
    }
}

var testClass2: TestClass2 = TestClass2()

Вывод

Вызов инициализации TestClass1!

Вызов deinit TestClass1!

Пример 2

import UIKit

internal final class TestClass1 {
    internal final var funcPointer: (() -> ())!

    internal init() {
        self.funcPointer = self.func1
        print("TestClass1 init is called!")
    }

    deinit {
        print("TestClass1 deinit is called!")
    }

    internal func func1() {
        print("func1 is called!")
    }
}

internal final class TestClass2 {
    init() {
        let testClass1: TestClass1 = TestClass1()
        testClass1.funcPointer()
    }
}

var testClass2: TestClass2 = TestClass2()

Вывод

Вызов инициализации TestClass1!

func1 вызывается!

Моя проблема в том, что метод deinit() никогда не вызывается в примере 2. Я думаю, что есть цикл сохранения, но я не знаю, какчтобы исправить это.

Я нашел этот пример и этот SO post , но я не могу реализовать его в своем примере кода.

1 Ответ

3 голосов
/ 28 мая 2019

Чтобы исправить это, вы должны вызвать func1 через слабое Я.

internal init() {
    self.funcPointer = { [weak self] in
        self?.func1()
    }
    print("TestClass1 init is called!")
}

Таким образом, вы можете предотвратить сохранение циклов.

В настоящий момент происходит назначениефункция экземпляра для вашего свойства экземпляра, которая теперь имеет строгую ссылку на вашу функцию.

Надеюсь, это поможет.

...