从特定的核心数据表行中检索值 - 然后将值存储到 UserDefaults

Posted

技术标签:

【中文标题】从特定的核心数据表行中检索值 - 然后将值存储到 UserDefaults【英文标题】:Retrieve value from specific core data table row - then store value to UserDefaults 【发布时间】:2018-09-10 12:12:26 【问题描述】:

我一般要做的事情: 1. 生成一个包含所有注册用户的表(存储在核心数据中)。 2.然后允许用户通过按一行来选择一个注册用户。 3. 当用户选择一行时,会打开一个包含详细用户信息的新页面。我正在尝试通过以下方式解决此问题: 1. 首先将给定单元格中的用户名存储到“UserDefaults.standard”中。 2. 然后在第二页,从“UserDefaults.standard”访问存储的用户名,并使用该动态值检索核心数据以获取更详细的用户信息。

问题: 我确信传递给“UserDefaults.standard”的数据是完整的表格,而不是来自特定单元格的数据。我通过使用“Print()”看到了这一点,实际上是显示所有行而不是只显示被选中的一行。 所以生成到第二页的 UserName 是一个更靠后的随机行(见图)。

    public class ViewController: UIViewController, UITableViewDataSource, UITableViewDelegate 

 var userNameobject : [NSManagedObject] = []

    @IBAction func pushTwo(_ sender: Any) 
    

    @IBOutlet weak var usersList: UITableView!

    override public func viewDidLoad() 
        super.viewDidLoad()

        usersList.register(UITableViewCell.self, forCellReuseIdentifier: "Cell")
    

    public override func viewWillAppear(_ animated: Bool) 
        super.viewWillAppear(animated)

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

        let managedContext = appDelegate.persistentContainer.viewContext
        let fetchRequest = NSFetchRequest<NSManagedObject>(entityName: "Users")

        do 
                userNameobject = try managedContext.fetch(fetchRequest)

                                             catch let error as NSError 
                                                print("Could not fetch. \(error), \(error.userInfo)")
                                            
    

      public func tableView(_ usersList: UITableView, numberOfRowsInSection section: Int) -> Int 
        return userNameobject.count

    

    public func tableView(_ usersList: UITableView, cellForRowAt indexPath: IndexPath)
        -> UITableViewCell 

            let person = userNameobject[indexPath.row]
            let cell = usersList.dequeueReusableCell(withIdentifier: "CellTwo", for: indexPath) as UITableViewCell
                cell.textLabel?.text = person.value(forKeyPath: "userName") as? String

            // STORE USERNAME
            let defaults = UserDefaults.standard
            defaults.set(person.value(forKeyPath: "userName"), forKey: "userNameDefault")

            return cell

    


    public func tableView(_ userList: UITableView, didSelectRowAt indexPath: IndexPath)
    

    

【问题讨论】:

永远不要使用UserDefaults 在控制器之间共享数据。使用 segue 并在索引路径处传递 NSManagedObject。并从实体中创建一个NSManagedObject 子类,这样更方便。为什么value(forKeyPath?有key,但没有path 为什么我永远不应该使用 UserDafults?您能否为 med 提供与我上面的代码兼容的 segue 解决方案,以便我尝试一下? UserDefaults 是临时数据的错误位置。在 Xcode 中创建一个新的 Master-Detail App 项目,您几乎可以免费获得全部代码。 PS:还有——另一个从不——从不guardAppDelegate。强行拆开!如果AppDelegate 丢失,您的应用甚至不会到达这条线。 我真的建议你阅读this answer 来回答类似的问题。 【参考方案1】:

1- 将 segue 源连接到 VC 而不是单元格

func tableView(_ userList: UITableView, didSelectRowAt indexPath: IndexPath)
 
   self.performSegue(withIdentifier: "toSecond", sender:userNameobject[indexPath.row])

2- 实施

override func prepare(for segue: UIStoryboardSegue, sender: Any?) 
    super.prepare(for: segue, sender: sender)

    if let des = segue.destination as? SecondVC 
         des.person = sender as! NSManagedObject
    


3-

class SecondVC:UIViewController 

    var person: NSManagedObject?


【讨论】:

感谢您的解决方案。我已经实现了这个,它似乎正在工作。唯一的问题是我看不到该特定行的值是否被传递。打印时我得到的唯一值是“[]”。您如何建议我将此对象转换为字符串以便生成用户名?【参考方案2】:

我通过给“发件人:”提供完全相同的行来解决这个问题,该行生成每个给定单元格的用户名。现在完美运行!

public func tableView(_ userList: UITableView, didSelectRowAt indexPath: IndexPath)

    let person = userNameobject[indexPath.row]
    let two =  person.value(forKeyPath: "userName") as? String
    self.performSegue(withIdentifier: "userLinkSegue", sender: two!)

    print(two!)

     // STORE USERNAME
     let defaults = UserDefaults.standard
     defaults.set(two!, forKey: "userNameDefault")


【讨论】:

以上是关于从特定的核心数据表行中检索值 - 然后将值存储到 UserDefaults的主要内容,如果未能解决你的问题,请参考以下文章

选中复选框时,数据表视图将值插入到字段中

从数据库中检索特定行并显示特定行中的所有数据并使用 php 发送 json

如何仅从系列或列表中获取特定值[关闭]

如何查询行中是不是存在值将值添加到另一个字段?

如何将值存储在列表或数组中并将所有值绑定到数据表然后gridview

如何从特定小时范围内的行中选择最小值?