Swift中嵌套字典下标赋值报Any?无下标错误的解决方法
报错原因
代码编译失败来自两个核心问题:
- 你用
let声明了current_data,Swift中Dictionary是值类型,let声明的实例完全不可变,无法执行任何赋值修改操作 - 外层字典的value类型被声明为
Any,通过下标current_data["data"]取到的返回值类型是Any?,编译器无法确认这个值是支持下标访问的字典类型,因此不允许直接对它做二次下标访问和赋值,就会抛出Value of type 'Any?' has no subscripts的错误。
正确实现方式
方案1:保留字典类型的写法
先把常量声明改为可变的var,再对内层字典做显式类型转换,修改完成后回写到外层字典即可:
// 将let改为var,允许字典修改 var current_data: [String : Any] = [ "table": "tasks", "data": ["title": title_of_task, "completed_by": date_of_task] ] if !description_of_task.isEmpty { // 取出内层值,转换为字符串key的字典类型 guard var innerData = current_data["data"] as? [String: Any] else { // 内层data不存在/类型不匹配时的异常处理,可根据业务逻辑调整 return } // 对内层字典赋值 innerData["description"] = description_of_task // 将修改后的内层字典回写到外层 current_data["data"] = innerData }
方案2:使用结构体建模(推荐)
如果字典结构固定,不要用[String: Any]这种无类型约束的字典,自定义结构体建模能获得编译期类型检查,不需要写繁琐的类型转换,也能避免大部分类型相关的运行时错误:
// 定义业务模型 struct TaskRequest { let table: String var data: TaskDetail } struct TaskDetail { var title: String var completed_by: Date var description: String? } // 初始化和赋值 var task = TaskRequest( table: "tasks", data: TaskDetail( title: title_of_task, completed_by: date_of_task, description: nil ) ) if !description_of_task.isEmpty { // 直接通过属性赋值,不需要类型转换,编译期自动检查合法性 task.data.description = description_of_task }
内容的提问来源于stack exchange,提问作者user15178581
相关产品推荐
相关产品推荐

