首页 > 解决方案 > Swift 中的 iOS 编程和内存管理

问题描述

我对 iOS 快速编程相当陌生。我目前正在处理我的一个项目,并且非常小心地只捕获对 self 的弱引用,检查是否调用了 deinit 等。但我注意到 xcode 中的 Debug navigator 中的内存指示器仍然随着时间的推移略有增加. 经过多次(数十次安装视图控制器然后将其关闭)后,我注意到内存已从 21.7MB 增加到 23.1MB。也许这是我的偏执狂,但我决定做一个测试。

所以我有一个干净的 Xcode 项目。默认项目ViewController有以下代码:

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        view.backgroundColor = .systemGray
        
        let button = UIButton(type: .custom)
        button.setTitle("Show", for: [])
        button.addTarget(self, action: #selector(showVC), for: .touchUpInside)
        
        view.addSubview(button)
        button.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            button.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            button.centerYAnchor.constraint(equalTo: view.centerYAnchor),
        ])
    }
    
    
    @objc func showVC() {
        let newVC = SecondVC()
        self.present(newVC, animated: true, completion: nil)
    }
}

第二个VC有以下代码:

class SecondVC: UIViewController {
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        view.backgroundColor = .systemYellow
        
        let button = UIButton(type: .custom)
        button.setTitle("Close", for: [])
        button.addTarget(self, action: #selector(closeVC), for: .touchUpInside)
        
        view.addSubview(button)
        button.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            button.centerXAnchor.constraint(equalTo: view.centerXAnchor),
            button.centerYAnchor.constraint(equalTo: view.centerYAnchor, constant: -20),
        ])
    }
    
    
    @objc func closeVC() {
        self.dismiss(animated: true, completion: nil)
    }
    
}

然后我用以下代码构建了一个 XCTestCase:

class testingMemoryUITests: XCTestCase {

    override func setUpWithError() throws {
        // Put setup code here. This method is called before the invocation of each test method in the class.

        // In UI tests it is usually best to stop immediately when a failure occurs.
        continueAfterFailure = false

        // In UI tests it’s important to set the initial state - such as interface orientation - required for your tests before they run. The setUp method is a good place to do this.
    }

    override func tearDownWithError() throws {
        // Put teardown code here. This method is called after the invocation of each test method in the class.
    }

    func testVCPresentation() {
        
        let app = XCUIApplication()
        
        let showButton = app/*@START_MENU_TOKEN@*/.staticTexts["Show"]/*[[".buttons[\"Show\"].staticTexts[\"Show\"]",".staticTexts[\"Show\"]"],[[[-1,1],[-1,0]]],[0]]@END_MENU_TOKEN@*/
        showButton.tap()
        
        let closeButton = app/*@START_MENU_TOKEN@*/.staticTexts["Close"]/*[[".buttons[\"Close\"].staticTexts[\"Close\"]",".staticTexts[\"Close\"]"],[[[-1,1],[-1,0]]],[0]]@END_MENU_TOKEN@*/
        closeButton.tap()
    }

    
    func testLaunchPerformance() throws {
        if #available(macOS 10.15, iOS 13.0, tvOS 13.0, watchOS 7.0, *) {
            // This measures how long it takes to launch your application.
            measure(metrics: [XCTApplicationLaunchMetric()]) {
             
                XCUIApplication().launch()

                var applicationLaunchCounter = 0
                while applicationLaunchCounter < 100 {
                
                    XCUIApplication().activate()

                    var counter = 0
                    while counter < 100 {
                        testVCPresentation()
                        counter += 1
                        print("Counter: ", applicationLaunchCounter, counter)
                    }
                    
                    XCUIApplication().terminate()
                    applicationLaunchCounter += 1
                }
            }
        }
    }
}

当我运行上面的代码时,它会启动应用程序,然后它会启动第二个视图控制器并关闭它 100 次。然后应用程序被关闭,然后我们重新开始 100 次。所以总的来说,测试将触发这 10,000 次。在这个测试开始时,我从 21.7MB 开始,到最后,内存为 83.2MB。CPU 在整个测试中保持在 4% 的低水平。

这是我应该担心的事情吗?虽然这些数字很低,但在像我这样的项目中,有更多的视图等,数字有点高,我以大约 162MB 结束测试。

8 月 26 日更新 我已经在模拟器和物理设备上运行了测试,并且观察到了相同的行为。

我还使用仪器检查泄漏,但没有发现任何泄漏。

标签: swiftxcodexctest

解决方案


推荐阅读