Why must delegate protocols inherit from `AnyObject` to prevent memory leaks?
Explanation & Code
Answer:
Delegate protocols must inherit from AnyObject to restrict protocol conformance to classes, allowing delegate properties to be marked with the weak keyword.
In Swift, protocols can be adopted by value types (struct, enum) or reference types (class). Because weak can only be applied to reference types managed on the heap, the Swift compiler emits a compilation error if you attempt to declare weak var delegate: SomeProtocol? on a protocol that does not conform to AnyObject.
If developers omit AnyObject and work around compiler errors by declaring var delegate: SomeProtocol? strongly, a bidirectional retain cycle occurs when a child view/controller references its parent controller.
Code Example:
// ❌ Error or strong retain cycle: protocol not constrained to classes
// protocol FeedCellDelegate { func didTapLike() }
// ✅ Constrain protocol to class instances with AnyObject
protocol FeedCellDelegate: AnyObject {
func didTapLike(on cell: FeedCell)
}
class FeedCell: UITableViewCell {
// weak requires AnyObject protocol conformance
weak var delegate: FeedCellDelegate?
func handleLikeButtonTap() {
delegate?.didTapLike(on: self)
}
}
class FeedViewController: UIViewController, FeedCellDelegate {
func didTapLike(on cell: FeedCell) {
print("Liked post in cell")
}
}
Key Points:
- Protocol inheritance:
protocol MyDelegate: AnyObjectreplaces the legacy Objective-Cprotocol MyDelegate: classsyntax - Always mark delegate properties as
weak var delegate: MyDelegate?to ensure child views do not retain parent controllers
Rate your understanding: