Skip to content

Instantly share code, notes, and snippets.

View uc-compass-bot's full-sized avatar

uc-compass-bot

View GitHub Profile
@uc-compass-bot
uc-compass-bot / lowMemoryWarningTracking.swift
Created October 15, 2019 14:16
Catch And Track Low Memory Warnings
@UIApplicationMain
final class AppDelegate: UIResponder, UIApplicationDelegate {
func applicationDidReceiveMemoryWarning(_ application: UIApplication) {
var properties: [String: String] = [:]
if let footprint = memoryFootprint {
properties["memory"] = String(format: "%d MB", footprint / 1024 / 1024)
}
// Trigger "Analytics Event" or "Non-Fatal Crash" or persist locally and send to server later
@uc-compass-bot
uc-compass-bot / retainCycle6.swift
Created October 15, 2019 14:16
Deinit View Controller
class ViewController: UIViewController {
deinit {
print("View Controller has been released") // Set breakpoint on this line
}
}
import Foundation
public class MemoryChecker {
public static func verifyDealloc(object: AnyObject?) {
#if DEBUG
DispatchQueue.main.asyncAfter(deadline: .now() + 5) { [weak object] in
if let object = object {
fatalError("Class Not Deallocated: \(String(describing: object.classForCoder ?? object)))")
}
}
@uc-compass-bot
uc-compass-bot / retainCycle1.swift
Created October 15, 2019 14:17
Catch Retain Cycles In Navigation Controller Subclass
import UIKit
class NavigationController: UINavigationController {
override func popViewController(animated: Bool) -> UIViewController? {
let viewController = super.popViewController(animated: animated)
MemoryChecker.verifyDealloc(object: viewController)
return viewController
}
}
@uc-compass-bot
uc-compass-bot / retainCycle2.swift
Created October 15, 2019 14:18
Catch Retain Cycles In Navigation Controller Subclass 2
import UIKit
class NavigationController: UINavigationController {
deinit {
viewControllers.forEach { MemoryChecker.verifyDealloc(object: $0) }
}
}
@uc-compass-bot
uc-compass-bot / retainCycle3.swift
Created October 15, 2019 14:19
Catch Retain Cycles In Table View Subclass
import UIKit
class TableView: UITableView {
private var allCells: [WeakBox<UITableViewCell>] = []
private func appendIfNotPresent(_ cell: UITableViewCell) {
if allCells.first(where: { $0.unbox === cell }) == nil {
allCells.append(WeakBox(cell))
}
}
@uc-compass-bot
uc-compass-bot / retainCycle4.swift
Created October 15, 2019 14:19
Catch Retain Cycles In Collection View Subclass
import UIKit
class CollectionView: UICollectionView {
private var allCells: [WeakBox<UICollectionViewCell>] = []
private func appendIfNotPresent(_ cell: UICollectionViewCell) {
if allCells.first(where: { $0.unbox === cell }) == nil {
allCells.append(WeakBox(cell))
}
}
@uc-compass-bot
uc-compass-bot / weakBox.swift
Created October 15, 2019 14:20
Catch Retain Cycles Weak Box
import Foundation
class WeakBox<A: AnyObject> {
weak var unbox: A?
init(_ value: A) {
unbox = value
}
}
@uc-compass-bot
uc-compass-bot / retainCycle2.swift
Created October 15, 2019 14:20
Example Of Retain Cycle On Delegate
class ParentViewController: UIViewController, ChildViewControllerProtocol {
let childViewController = ChildViewController()
func prepareChildViewController() {
childViewController.delegate = self // ❌ Strong reference, retain cycle
}
}
protocol ChildViewControllerProtocol: class {}
@uc-compass-bot
uc-compass-bot / retainCycle2-Fix.swift
Created October 15, 2019 14:21
Example Of Retain Cycle On Delegate - Fix
weak var delegate: ChildViewControllerProtocol? // ✅ No retain cycle