You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用UserDefaults保存数据报非属性列表对象插入错误如何解决

问题根因

点击保存触发的报错翻译如下:

线程1报错:"尝试插入非属性列表对象 <UITextField: 0x7fea4d02ca00; frame = (20 85; 374 34); opaque = NO; autoresize = RM+BM; gestureRecognizers = <NSArray: 0x600002cb65b0>;; placeholder = Name; borderStyle = RoundedRect; background = <_UITextFieldSystemBackgroundProvider: 0x6000022fa7c0: backgroundView=<_UITextFieldRoundedRectBackgroundViewNeue: 0x7fea4c7107c0; frame = (0 0; 374 34); opaque = NO; autoresize = W+H; userInteractionEnabled = NO; layer = <CALayer: 0x6000022fa7e0>>, fillColor=(null), textfield=<UITextField 0x7fea4d02ca00>>; layer = <CALayer: 0x6000022fa580>> 对应键 personName"

崩溃的核心原因是你往UserDefaults中传入了不支持存储的类型:UserDefaults仅支持存储属性列表类型(NSString、NSNumber、NSData、NSDate、NSArray、NSDictionary),你在保存逻辑里直接把UITextField控件实例存了进去,没有取输入框内的文本值,自然触发报错。

代码问题点

你当前保存按钮的代码存在两处核心错误:

// 错误:传入的是nameTextField控件对象,不是输入框内的字符串内容
UserDefaults.standard.set(nameTextField!, forKey: "personName")
// 错误:传入的是birthdayTextField控件对象,不是输入框内的字符串内容
UserDefaults.standard.set(birthdayTextField, forKey: "personDate")

nameLabel.text = "Name: \(nameTextField.text!)"
birthdayLabel.text = "Birthday: \(birthdayTextField.text!)"

另外viewDidLoad中的读取逻辑也有小问题:读取后给标签赋值没有和保存逻辑保持一致的前缀格式,会导致首次加载本地数据时显示内容和保存后格式不统一,而且用object(forKey:)再强转String的写法不如直接用专属取值方法安全。

修复代码

修正保存按钮点击逻辑

存储时取输入框的text属性,同时做空值兜底,避免强制解包引发的异常:

// 安全获取输入内容,空值默认用空字符串兜底
let inputName = nameTextField.text ?? ""
let inputBirthday = birthdayTextField.text ?? ""

// 存储字符串类型的输入内容,而非控件本身
UserDefaults.standard.set(inputName, forKey: "personName")
UserDefaults.standard.set(inputBirthday, forKey: "personDate")

// 标签赋值保持格式统一
nameLabel.text = "Name: \(inputName)"
birthdayLabel.text = "Birthday: \(inputBirthday)"

修正viewDidLoad读取逻辑

直接用string(forKey:)读取字符串值,赋值时保持格式和保存逻辑一致:

// 直接读取字符串类型值,空值兜底
let storedName = UserDefaults.standard.string(forKey: "personName") ?? ""
let storedDate = UserDefaults.standard.string(forKey: "personDate") ?? ""

if !storedName.isEmpty {
    nameLabel.text = "Name: \(storedName)"
}

if !storedDate.isEmpty {
    birthdayLabel.text = "Birthday: \(storedDate)"
}

内容的提问来源于stack exchange,提问作者althebeast

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 08:54:19