我想对现有的NWInterface类的实例进行编码,它有一个类型为NWInterface.InterfaceTypetype字段,即enum.

有什么方法可以轻松地将Encodable接口添加到该嵌套类型中吗?目前,我的解决方法是在包含类的扩展中处理编码:

extension NWInterface : Encodable {

    enum CodingKeys: CodingKey {
        case name
        case type
    }

    public func encode(to encoder: Encoder) throws {
        var container = encoder.container(keyedBy: CodingKeys.self)
        try container.encode(name, forKey: .name)
        switch type {
            case .wifi:
                try container.encode("wifi", forKey: .type)
            case .cellular:
                try container.encode("cellular", forKey: .type)
            case .wiredEthernet:
                try container.encode("ethernet", forKey: .type)
            case .loopback:
                try container.encode("loopback", forKey: .type)
            case .other:
                try container.encode("other", forKey: .type)
            default:
                try container.encode("unknown", forKey: .type)
        }
    }
}

这感觉像是unsatisfactory,特别是对于我自己定义的enum个类型,我可以简单地在定义时添加Encodable接口,并"免费"获得实现.

推荐答案

您可以向嵌套的枚举添加Encodable一致性吗?

你是免费得到的吗,就像你自己的枚举一样?

不是的.我不知道为什么,但自动Codable合成似乎要求扩展名与structclassenum在同一文件中.

下面是扩展嵌套enum的实现应该是什么样子.

extension NWInterface : Encodable {
    enum CodingKeys : CodingKey {
        case name, type
    }
    public func encode(to encoder: Encoder) throws {
        var container = encoder.container(keyedBy: CodingKeys.self)
        try container.encode(name, forKey: .name)
        try container.encode(type, forKey: .type)
    }
}

extension NWInterface.InterfaceType : Encodable {
    public func encode(to encoder: Encoder) throws {
        var container = encoder.singleValueContainer()
        switch self {
            case .wifi:
                try container.encode("wifi")
            case .cellular:
                try container.encode("cellular")
            case .wiredEthernet:
                try container.encode("ethernet")
            case .loopback:
                try container.encode("loopback")
            case .other:
                try container.encode("other")
            default:
                try container.encode("unknown")
        }
    }
}

您还可以将第二个扩展压缩为:

extension NWInterface.InterfaceType : Encodable {
    public func encode(to encoder: Encoder) throws {
        var container = encoder.singleValueContainer()
        try container.encode("\(self)")
    }
}

如果您采取适当的措施来处理Decoder中的意外字符串.

Swift相关问答推荐

避免嵌套导航TabView

不使用`lockFocus`将两个重叠的NSImage转换为单个NSImage

Swift:iVar + Equatable上的协议约束

如何让ScrollView缩小到合适的大小,并在没有黑客攻击的情况下占用最小空间

SwiftUI-如何使用剩余时间制作倒计时计时器

在Swift中如何将NSUrl转换为本地路径URL

如何在 macOS/AppKit 的窗口选项卡上接受拖动项目的放置?

URL appendPathComponent(_:) 已弃用?

Firebase removeObserver 在 Swift 5 中不起作用

如何在 AppDelegate for Cocoa macOS 中创建 mainMenu 和菜单项?

我怎样才能缩短(提高效率)这段代码?

与 SwiftUI 中的 onChange 修饰符相比,objectWillChangeSequence 的目的是什么?

使 Swift 并发中的任务串行运行

RealityKit – 无法加载 ARView(发现为零)

无法从自定义动态框架(Swift)访问类

是 swift 中另一个日期的同一周、月、年的日期

playground 导入:没有这样的模块Foo

UILabel 文本不换行

如何快速从另一个视图控制器重新加载表格视图

保持窗口始终在顶部?