尝试设置非 属性 列表对象时出现 Userdefault 错误

Userdefault error with Attempt to set a non-property-list object

我尝试将数组保存到 UserDefault,但尝试设置非 属性-list 对象时出错。我从去年开始就知道如何使用 UserDefault,但此时,对我来说是新的,我没有体验过用多个字符串保存数组。将数组保存到 UserDefaults 的最佳方法是什么?我试着在网上四处看看,但大多数都是旧的 swift,而且它们看起来不像我的数组。这是我的代码:

var currentWeatherUnit: [(temperature:String, measurement:String)])] = []

func checkingForSetting(completion: @escaping (() -> Void)) {
   if let getsetting = UserDefaults.standard.array(forKey: "Current Weather Setting") {
      currentWeatherUnit = getsetting as! [(temperature: String, measurement: String)]
      print("Current weather setting is exist")
   } else {
   currentWeatherUnit = [(temperature: "C", measurement: "mm")]
      UserDefaults.standard.set(currentWeatherUnit, forKey: "Current Weather Setting")
      print("Create new setting for current weather")
   }
}

崩溃日志:

2020-06-19 16:32:17.354822-0600 Playground Phy[5800:1787752] [User Defaults] Attempt to set a non-property-list object ( "(temperature: \"C\", measurement: \"mm\")" ) as an NSUserDefaults/CFPreferences value for key Current Weather Setting 2020-06-19 16:32:17.355108-0600 Playground Phy[5800:1787752] * Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Attempt to insert non-property list object ( "(temperature: \"C\", measurement: \"mm\")" ) for key Current Weather Setting' * First throw call stack: (0x193cda300 0x1939eec1c 0x193d335a8 0x193d07ab4 0x193d08190 0x193d07e7c 0x193d08250 0x193baffb0 0x193d10838 0x193c403bc 0x193c3fc04 0x193bac83c 0x193baf9d4 0x193d13cc8 0x193fda118 0x104464dc0 0x104464140 0x104464928 0x1977b0aac 0x1977b5660 0x1977b5a4c 0x197e5c264 0x197e5b960 0x197e5c8f0 0x197e6db44 0x198072a10 0x1973f8a2c 0x197e1ef9c 0x197e1f320 0x1979a1e08 0x198f3cffc 0x198f635a0 0x198f47ebc 0x198f63234 0x1049d718c 0x1049da964 0x198f896c4 0x198f89370 0x198f898dc 0x193c55af4 0x193c55a48 0x193c55198 0x193c4ff38 0x193c4f8f4 0x19e066604 0x197e23358 0x10446baec 0x193acb2dc) libc++abi.dylib: terminating with uncaught exception of type NSException

请仔细阅读错误信息,很清楚。

Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Attempt to insert non-property list object ( "(temperature: \"C\", measurement: \"mm\")" ) for key Current Weather Setting'

列表对象是一个元组,不符合属性列表。

一个合理的解决方案是自定义结构和 Codable,完成处理程序毫无意义,因为 UserDefaults 是同步的。

struct WeatherUnit : Codable {
    let temperature, measurement : String
}

var currentWeatherUnit = [WeatherUnit]()

func checkingForSetting() {
    if let data = UserDefaults.standard.data(forKey: "Current Weather Setting") {
        do {
            currentWeatherUnit = try PropertyListDecoder().decode([WeatherUnit].self, from: data)
            print("Current weather setting is exist")
        } catch { print(error) }
    } else {
        currentWeatherUnit = [WeatherUnit(temperature: "C", measurement: "mm")]
        let data = try? PropertyListEncoder().encode(currentWeatherUnit)
        UserDefaults.standard.set(data, forKey: "Current Weather Setting")
        print("Create new setting for current weather")
    }
}