使用didSet导致函数多次运行

问题描述 投票:-1回答:2

为了从先前的viewController获得的值中,我使用didSet上的结构。

class ReviewViewController:  UIViewController, UITextFieldDelegate {
var detailBuilding: Building? {
    didSet {
        configureView()
    }

}

override func viewDidLoad() {
    super.viewDidLoad()
    configureView()
    CKContainer.default()

}

override func viewWillAppear(_ animated: Bool) {
    print("this override ran")
    navigationItem.hidesBackButton = false

}

func configureView() {
    let appDelegate = UIApplication.shared.delegate as! AppDelegate
    let context = appDelegate.persistentContainer.viewContext
    let request = NSFetchRequest<NSFetchRequestResult>(entityName: "RatingAttributes")
    print("the buildingID is \(String(describing: detailBuilding?.buildingID))")

    request.predicate = NSPredicate(format: "buildingID == %@", String(describing: detailBuilding?.buildingID))
    print("configuration ran")
    do {
        let result = try context.fetch(request)
        //assert(result.count < 2)
        //print("the result we got was \(result[0])")
        for data in result as! [NSManagedObject] {
            print("The data was \(data.value(forKey: "buildingID")) ")
        }
    } catch {

        print("Failed to retreive core data")
    }
}

}

然而,使用打印语句在func configureView(),我可以告诉大家,函数运行3次。但是,如果我删除电话从configureView()viewWillAppear(),那么该视图将不会出现;如果我从didSet删除它,然后detailBuilding(例如detailBuilding.rating)的值将是零。虽然功能运行第三次,detailBuilding的值始终为零,无论如何,这意味着我不能使用它们。

在前面的viewController我有:

@objc func addReviewAction(_ sender: UIButton) {
    print("ran this correctly")
    //navigationController?.setNavigationBarHidden(true, animated: true)
    let controller = ReviewViewController()
    controller.detailBuilding = detailBuilding
    controller.navigationItem.title = ""
    navigationItem.hidesBackButton = true
    let backItem = UIBarButtonItem()
    backItem.title = ""
    backItem.tintColor = #colorLiteral(red: 0.8039215803, green: 0.8039215803, blue: 0.8039215803, alpha: 1)
    navigationController?.navigationItem.backBarButtonItem = backItem
    navigationController?.pushViewController(ReviewViewController(), animated: true)

}

我检查了多次,以确保我不小心从别的地方调用configureView()。

我的问题是:为什么configureView()运行多次吗?为什么是第三detailBuilding零开出3次。我应该使用不同的方法获取detailBuilding,因为我需要它包含了我的NSPredicate值。

谢谢。

ios swift swift4 viewcontroller
2个回答
1
投票

从您刚才给出的代码应该只有 一 configureView()的两个电话

  1. didSet制作,执行controller.detailBuilding = detailBuilding之后。
  2. 对象初始化之后,从viewDidLoad制成

话虽这么说,你需要提供更多的代码,尤其是:

viewWillAppear()ReviewViewController和代码触发显示ReviewViewController

编辑:

感谢您的详细信息:)

你要排队一个问题:navigationController?.pushViewController(ReviewViewController(), animated: true)

它应该是navigationController?.pushViewController(controller, animated: true)

这就是为什么你有nil。您显示品牌现在的ViewController不相关的有detailBuilding注入的一个。

这就是为什么你有configureView()方法的3个电话:

  1. controllerReviewViewController的viewDidLoad中
  2. 从注射(didSet)
  3. 类型ReviewViewController的未命名的对象,什么也没有的viewDidLoad中注入,therfore与nil里面的detailBuilding在第三个呼叫。

2
投票

您正在创建ReviewViewController的两个实例,并设置只对其中的一个细节

// 1st instance
let controller = ReviewViewController() 
controller.detailBuilding = detailBuilding
controller.navigationItem.title = ""
navigationItem.hidesBackButton = true
let backItem = UIBarButtonItem()
backItem.title = ""
backItem.tintColor = #colorLiteral(red: 0.8039215803, green: 0.8039215803, blue: 0.8039215803, alpha: 1)
navigationController?.navigationItem.backBarButtonItem = backItem

// 2nd instance, first is deallocated and never used.
navigationController?.pushViewController(ReviewViewController(), animated: true)
// replace with:
navigationController?.pushViewController(controller, animated: true)
© www.soinside.com 2019 - 2024. All rights reserved.