设置CoreData的默认值

d0x*_*i45 1 core-data ios swift

我正在使用CoreData进行第一个项目,并且已经建立了数据模型。

我有一个带有添加按钮的表视图,该按钮触发警报并允许用户输入字符串:

func handleAdd() {

    let alert = UIAlertController(title: "New Company", message: "Add a new company", preferredStyle: .alert)

    let saveAction = UIAlertAction(title: "Save", style: .default) {
        [unowned self] action in

        guard let textField = alert.textFields?.first,
            let newCompany = textField.text else {
                return
        }

        self.save(name: newCompany)
        self.tableView.reloadData()
    }

    let cancelAction = UIAlertAction(title: "Cancel", style: .default)

    alert.addTextField()
    alert.addAction(saveAction)
    alert.addAction(cancelAction)

    present(alert, animated: true)
}
Run Code Online (Sandbox Code Playgroud)

该字符串将添加到NSManagedObject数组中:

func save(name: String) {

    guard let appDelegate =
        UIApplication.shared.delegate as? AppDelegate else {
            return
    }

    // 1
    let managedContext =
        appDelegate.persistentContainer.viewContext

    // 2
    let entity =
        NSEntityDescription.entity(forEntityName: "Company",
                                   in: managedContext)!

    let company = NSManagedObject(entity: entity,
                                 insertInto: managedContext)

    // 3
    company.setValue(name, forKeyPath: "name")



    // 4
    do {
        try managedContext.save()
        companies.append(company)
    } catch let error as NSError {
        print("Could not save. \(error), \(error.userInfo)")
    }
}
Run Code Online (Sandbox Code Playgroud)

到目前为止,一切看起来都很不错,除了我希望应用程序启动时已经有5个单元格,然后让用户根据需要添加/删除。如何设置要启动应用程序的5个默认值?我尝试将以下代码添加到viewWillAppear

    let entity =
        NSEntityDescription.entity(forEntityName: "Company",
                                   in: managedContext)!

    let company = NSManagedObject(entity: entity,
                                  insertInto: managedContext)

    company.setValue("Apple", forKeyPath: "name")
    company.setValue("Google", forKeyPath: "name")
    company.setValue("Facebook", forKeyPath: "name")
    company.setValue("Tesla", forKeyPath: "name")
    company.setValue("Twitter", forKeyPath: "name")

    self.save(name: "Apple")
    self.save(name: "Google")
    self.save(name: "Facebook")
    self.save(name: "Tesla")
    self.save(name: "Twitter")
Run Code Online (Sandbox Code Playgroud)

在加载时,它们全部出现。然后,当我离开页面并返回时,它们又被添加了。我知道这是因为它们在viewWillAppear中,并在每次页面加载时被调用。

苹果的文档(《核心数据编程指南》)作为初学者有点难以接受,但他们确实说

对于小型数据集,直接在代码中创建托管对象。

如果您正在使用iOS或为OS X创建的不是基于文档的应用程序,则可以在应用程序启动时添加检查,以确定在为应用程序商店指定的位置是否存在文件。如果不是,则需要导入数据。

我相信第二个代码段正是我要寻找的内容(如果输入错误,请更正我),但是我不确定如何实现它,因此,如何设置这些默认值的任何帮助都将其添加一次(加载),只有一次将不胜感激!

如果感兴趣的是初始化器

var companies = [NSManagedObject]()
var container: NSPersistentContainer!
let managedContext = (UIApplication.shared.delegate as! AppDelegate).persistentContainer.viewContext
let companyEntity = "Company"
Run Code Online (Sandbox Code Playgroud)

编辑:代码已添加到应用程序委托

    let vc = ViewController()
    let entity = NSEntityDescription.entity(forEntityName: "Company", in: managedContext)!
    let company = NSManagedObject(entity: entity,insertInto: managedContext)
    let userDefaults = UserDefaults.standard
    userDefaults.set(true, forKey: "firstRun")

    if userDefaults.valueForKey("firstRun") == true {

        company.setValue("Apple", forKeyPath: "name")
        company.setValue("Google", forKeyPath: "name")
        company.setValue("Facebook", forKeyPath: "name")
        company.setValue("Tesla", forKeyPath: "name")
        company.setValue("Twitter", forKeyPath: "name")

        vc.save(name: "Apple")
        vc.save(name: "Google")
        vc.save(name: "Facebook")
        vc.save(name: "Tesla")
        vc.save(name: "Twitter")

        userDefaults.set(false, forKey: "firstRun")
    }
Run Code Online (Sandbox Code Playgroud)

vad*_*ian 5

根据我的评论以及EDIT之后您(显然是失败的)代码,这是如何实现的建议firstRun

首先在中注册默认值applicationDidFinishLaunching,即使同时更改了默认值,也需要这些行。

let userDefaults = UserDefaults.standard
let defaultValues = ["firstRun" : true]
userDefaults.register(defaults: defaultValues)
Run Code Online (Sandbox Code Playgroud)

然后检查值(UserDefaults具有bool(forKey功能)并创建公司。使用默认值之前执行注册默认值的代码至关重要。

if userDefaults.bool(forKey: "firstRun") {

    let defaultCompanies = ["Apple", "Google", "Facebook", "Tesla", "Twitter"]
    let entity = NSEntityDescription.entity(forEntityName: "Company", in: managedContext)!

    for companyName in defaultCompanies {
        let company = NSManagedObject(entity: entity,insertInto: managedContext)
        company.setValue(companyName, forKey: "name") // not keyPath
        companies.append(company)
    }
    do {
        try managedContext.save()
        userDefaults.set(false, forKey: "firstRun")
    } catch let error as NSError {
        print("Could not save. \(error), \(error.userInfo)")
    }
}
Run Code Online (Sandbox Code Playgroud)

在您的代码中,您要创建一个公司并更改名称值5次而不保存该特定公司。实际上,该代码不执行任何操作。