arrays - 如何将包含数组的 Swift 对象自定义编码为 JSON?
问题描述
我是一名新手开发人员,正在编写一个 iOS 应用程序,该应用程序允许用户在一段录制的音乐中定义和重播多个“段落”,每个段落多次。
我的类 'Piece' 是一个 Observable 对象,它当前仅包含已发布的 var 'passages'(包含用户希望重播的段落详细信息的记录数组)。虽然 Piece 的唯一成员现在是一个“通道”数组,但我希望 Piece 最终会有更多成员,而不是数组。
我希望能够将用户定义的每个 Piece 保存为 JSON 文件。因为 'Piece' 是一个可观察的对象,所以它不符合 Codable 除非我编写自定义编码和解码函数。到目前为止,我一直无法找到任何示例代码来说明如何编码一个对象(在我的情况下为“Piece”),而该对象又包含一个自定义对象数组(在我的情况下为“Passage”),这些对象有多个特性。
下面显示了我的“Piece”和“Passage”代码的相关部分。
class Piece: ObservableObject, Codable {
@Published var passages = [Passage]()
enum CodingKeys: CodingKey {
case passages
}
init() { }
required init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
passages = try container.decode([Passage].self, forKey: .passages)
}
func encode(to encoder: Encoder) throws {
var container = encoder.container(keyedBy: CodingKeys.self)
try container.encode([Passage](), forKey: .passages)
}
}
struct Passage: Codable, Equatable, Identifiable, Hashable {
var id = UUID()
var startTime: Double
var endTime: Double
var extraPause: Double
var numIterations: Int
var skipMe: Bool = false
enum PassageKeys: CodingKey {
case id, startTime, endTime, extraPause, numIterations, skipMe
}
func encode(to encoder: Encoder) throws {
var container = encoder.container(keyedBy: PassageKeys.self)
try container.encode(id, forKey: .id)
try container.encode(startTime, forKey: .startTime)
try container.encode(endTime, forKey: .endTime)
try container.encode(extraPause, forKey: .extraPause)
try container.encode(numIterations, forKey: .numIterations)
try container.encode(skipMe, forKey: .skipMe)
}
}
在我的应用程序界面中,我编写了以下按钮操作。
let url = self.getDocumentsDirectory().appendingPathComponent("X.json")
let encoder = JSONEncoder()
do {
let data = try encoder.encode(self.piece)
let string = String(data: data, encoding: .utf8)!
print("Here is the string we are trying to write: \(string)")
try string.write(to: url, atomically: true, encoding: .utf8)
} catch {
print(error.localizedDescription)
}
当我用几条记录填充“通道”数组然后单击触发此操作的按钮时,控制台输出显示:
Here is the string we are trying to write: {"passages":[]}
在 Passage.encode() 函数中设置断点表明该函数永远不会被调用。
谁能帮我指出正确的方向?
解决方案
你应该改变
try container.encode([Passage](), forKey: .passages)
至
try container.encode(passages, forKey: .passages)
在你的代码中。否则,您总是试图对刚刚创建的新空数组进行编码[Passage]()
。
推荐阅读
- visual-studio-code - 更漂亮的扩展在 vs 代码中不起作用
- sql - 如何使用 SQL 使用一个命令更改/更改多个列的名称?
- laravel - 模型启动事件在 Laravel 7 中没有触发
- python - 为什么 pd.reset_index 将 Series 转换为 DataFrame
- python - 如何使用 Matplotlib 绘制具有非线性 x 轴刻度的曲线?
- python - 如何使用 Python 根据当前值填充缺失值?
- javascript - 根据 AJAX 响应启动计时器
- r - 如何更改此 ggplot 代码以使其与导入的 excel 数据一起使用?
- javascript - 如何在Javascript中对forEach循环应用条件?
- android - Flutter - 如何检测webview中特定按钮的点击?