Consider this Swift class with a closure property capturing self. What will be printed when example.run() is called?
class Example { var value = 10 lazy var closure: () -> Void = { print("Value is \(self.value)") } func run() { closure() } } let example = Example() example.run()
Think about how self is captured in the closure and what value is initialized to.
The closure captures self strongly by default, but since value is 10, it prints "Value is 10". No retain cycle occurs here because the closure is lazy and used within the class.
Given this Swift code, what will be the output or behavior?
class Person { let name: String lazy var greet: () -> Void = { print("Hello, \(self.name)!") } init(name: String) { self.name = name } deinit { print("Person \(name) is being deinitialized") } } var person: Person? = Person(name: "Alice") person?.greet() person = nil
Think about how the closure captures self and what happens when person is set to nil.
The closure captures self strongly, so the Person instance is never deinitialized, causing a memory leak. The greet prints correctly, but the deinit message never appears.
Examine the following Swift code. Why does the ViewController instance never get deinitialized?
class ViewController { var completionHandler: (() -> Void)? func setup() { completionHandler = { print("ViewController is running") self.doSomething() } } func doSomething() { print("Doing something") } deinit { print("ViewController deinitialized") } } var vc: ViewController? = ViewController() vc?.setup() vc = nil
Think about how closures capture variables and how that affects object lifetime.
The closure assigned to completionHandler captures self strongly. Since ViewController holds the closure and the closure holds self, a retain cycle occurs, preventing deinitialization.
Given the retain cycle in the previous example, which closure syntax correctly uses a weak capture of self to avoid the cycle?
class Controller { var handler: (() -> Void)? func configure() { handler = { /* capture self weakly here */ self?.action() } } func action() { print("Action executed") } deinit { print("Controller deinitialized") } }
Consider how to safely capture self without causing a retain cycle.
Option A uses [weak self] to capture self weakly, preventing retain cycles. Option A uses unowned which can cause crashes if self is nil. Option A captures self strongly. Option A is invalid syntax.
Analyze this Swift code snippet. After manager = nil, how many Task instances remain in memory?
class Task { let id: Int init(id: Int) { self.id = id } deinit { print("Task \(id) deinitialized") } } class Manager { var tasks: [Task] = [] lazy var taskHandler: () -> Void = { [weak self] in guard let self else { return } for task in self.tasks { print("Handling task \(task.id)") } } func addTask(_ task: Task) { tasks.append(task) } deinit { print("Manager deinitialized") } } var manager: Manager? = Manager() manager?.addTask(Task(id: 1)) manager?.addTask(Task(id: 2)) manager?.taskHandler() manager = nil
Think about ownership and how weak capture affects object lifetime.
The Manager holds strong references to Task instances in its array. When manager is set to nil, the Manager and its tasks are deinitialized. The closure captures self weakly, so no retain cycle occurs.