如何快速将 NSIndexPath 添加到 NSUserDefaults

Posted

技术标签:

【中文标题】如何快速将 NSIndexPath 添加到 NSUserDefaults【英文标题】:How to add NSIndexPath to NSUserDefaults in swift 【发布时间】:2016-05-03 10:26:08 【问题描述】:

我正在尝试将NSIndexPath 保存在NSUserDefaults,但出现以下异常:-

尝试将非属性列表对象 length = 2, path = 0 - 12 设置为 键 LastSelectedIndeX 的 NSUserDefaults/CFPreferences 值

我的代码:-

let selectedIndexPath = tableView.indexPathForSelectedRow
   NSUserDefaults.standardUserDefaults().setObject(selectedIndexPath, forKey: "lastSelectedIndex")
   NSUserDefaults.standardUserDefaults().synchronize()

那么我如何保存NSIndexPath 以便稍后在另一个视图控制器上使用它。

【问题讨论】:

【参考方案1】:

你不能在 NSUserDefault 中直接保存 indexPath。您可以将 NSArray 、 NSDictionary 、 NSNumber 、 NSString 和 NSDictionary 存储在 NSUserDefault 中。

使用 NSKeyedArchiver 存储 IndexPath:

let data = NSKeyedArchiver.archivedDataWithRootObject(selectedIndexPath)
NSUserDefaults.standardUserDefaults().setObject(data, forKey: "indexKey")

使用NSKeyedArchiver获取IndexPath:

let data1 = NSUserDefaults.standardUserDefaults().objectForKey("indexKey") as? NSData
let indexP1 = NSKeyedUnarchiver.unarchiveObjectWithData(data1!) as! NSIndexPath

【讨论】:

好吧,您没有将其存储为字典。您可以使用"1.2.3.4" 形式将路径编码为字符串。【参考方案2】:

正如其他人所提到的,(NS)IndexPath 不符合属性列表。

解决方案是使用UserDefaults 的这个简单扩展将IndexPath 保存为两个整数的数组

extension UserDefaults 

  func indexPath(forKey key : String) -> IndexPath?
  
    guard let indexArray = array(forKey: key) as? [Int] else  return nil 
    return IndexPath(row: indexArray[0], section: indexArray[1])
  

  func set(_ indexPath : IndexPath, forKey key: String)
  
    set([indexPath.row, indexPath.section], forKey: key)
  

您可以在编辑历史记录中找到旧 Swift 版本的语法。

【讨论】:

为什么只有两个整数? @***foe 为什么不呢? simple 形式就是rowsection 但索引路径可以超过 2 级深度。 @***foe 我知道,但问题显然是关于UITableView【参考方案3】:

你可以这样做,

保存喜欢,

  var myDefaults: NSUserDefaults = NSUserDefaults.standardUserDefaults()
    var indexPath: NSIndexPath = self.myTableView.indexPathForSelectedRow
    var data: NSData = NSKeyedArchiver.archivedDataWithRootObject(indexPath)
    myDefaults["lastSelectedIndex"] = myDefaults

检索喜欢,

    var data2: NSData = myDefaults.dataForKey("lastSelectedIndex")
    var indexPath2: NSIndexPath = NSKeyedUnarchiver.unarchiveObjectWithData(data2)

您必须将 indexpath 转换为数据,然后才能保存和检索。

希望这会有所帮助:)

【讨论】:

【参考方案4】:

此 Swift 代码适用于任何深度的 IndexPath

extension UserDefaults 
    func indexPath(forKey key: String) -> IndexPath? 
        if let data = data(forKey: key), let indexPath = try? JSONDecoder().decode(IndexPath.self, from: data) 
            return indexPath
        
        return nil
    
    func set(_ indexPath: IndexPath, forKey key: String) 
        if let data = try? JSONEncoder().encode(indexPath) 
            set(data, forKey: key)
        
    

【讨论】:

以上是关于如何快速将 NSIndexPath 添加到 NSUserDefaults的主要内容,如果未能解决你的问题,请参考以下文章

通过已知的 NSIndexPath 快速获取单元格

如何将 NSIndexPath 转换为 NSInteger?

在字典中添加 NSIndexPath 作为键和 NSNumber 作为值的问题?

如何将 NSIndexPath 转换为 NSString-iOS

Objective-C:如何将 NSIndexSet 转换为 NSIndexPath

如何动态向 UITableView 添加行? [关闭]