标签: codable

Swift 4 JSON可解码最简单的解码类型更改方法

使用swift4的Codable协议,有很多级别的引擎日期和数据转换策略.

鉴于JSON:

{
    "name": "Bob",
    "age": 25,
    "tax_rate": "4.25"
}
Run Code Online (Sandbox Code Playgroud)

我想将它强制进入以下结构

struct ExampleJson: Decodable {
    var name: String
    var age: Int
    var taxRate: Float

    enum CodingKeys: String, CodingKey {
       case name, age 
       case taxRate = "tax_rate"
    }
}
Run Code Online (Sandbox Code Playgroud)

日期解码策略可以将基于字符串的日期转换为日期.

基于String的Float是否有某种功能

否则我一直坚持使用CodingKey引入一个String并使用计算得到:

    enum CodingKeys: String, CodingKey {
       case name, age 
       case sTaxRate = "tax_rate"
    }
    var sTaxRate: String
    var taxRate: Float { return Float(sTaxRate) ?? 0.0 }
Run Code Online (Sandbox Code Playgroud)

这种方式比我看起来需要更多的维护.

这是最简单的方式还是类似于DateDecodingStrategy用于其他类型的转换?

更新:我应该注意:我也走了超越的路线

init(from decoder:Decoder)
Run Code Online (Sandbox Code Playgroud)

但这是相反的方向,因为它迫使我为自己做这一切.

json swift swift4 codable

24
推荐指数
3
解决办法
1万
查看次数

使用Codable序列化为JSON时Swift String转义

我正在尝试将我的对象序列化如下:

import Foundation

struct User: Codable {
    let username: String
    let profileURL: String
}

let user = User(username: "John", profileURL: "http://google.com")

let json = try? JSONEncoder().encode(user)

if let data = json, let str = String(data: data, encoding: .utf8) {
    print(str)
}
Run Code Online (Sandbox Code Playgroud)

但是在macOS上我得到以下内容:

{"profileURL":"http:\/\/google.com","username":"John"}
Run Code Online (Sandbox Code Playgroud)

(注意转义'/'字符).

在Linux机器上,我得到:

{"username":"John","profileURL":"http://google.com"}
Run Code Online (Sandbox Code Playgroud)

如何让JSONEncoder在macOS上返回未转义的表单?

我需要JSON中的字符串严格未转义.

macos json ios swift codable

24
推荐指数
3
解决办法
8478
查看次数

使用Decodable进行JSON解析时,optional和decodeIfPresent有什么区别?

Codable第一次使用Swift 4的协议,我无法理解使用decodeIfPresentfrom Decodable.

/// Decodes a value of the given type for the given key, if present.
///
/// This method returns `nil` if the container does not have a value associated with `key`, or if the value is null. The difference between these states can be distinguished with a `contains(_:)` call.
///
/// - parameter type: The type of value to decode.
/// - parameter key: The key that the decoded value is associated …
Run Code Online (Sandbox Code Playgroud)

swift swift4 codable decodable

23
推荐指数
3
解决办法
7532
查看次数

Swod 4中的默认情况下的Codable枚举

我已定义enum如下:

enum Type: String, Codable {
    case text = "text"
    case image = "image"
    case document = "document"
    case profile = "profile"
    case sign = "sign"
    case inputDate = "input_date"
    case inputText = "input_text"
    case inputNumber = "input_number"
    case inputOption = "input_option"

    case unknown
}
Run Code Online (Sandbox Code Playgroud)

映射JSON字符串属性.自动序列化和反序列化工作正常,但我发现如果遇到不同的字符串,反序列化将失败.

是否可以定义一个unknown映射任何其他可用案例的案例?

这可能非常有用,因为这些数据来自RESTFul API,可能会在将来发生变化.

enums ios swift swift4 codable

22
推荐指数
5
解决办法
6259
查看次数

Swift的JSONDecoder在JSON字符串中有多种日期格式?

Swift JSONDecoder提供了一个dateDecodingStrategy属性,允许我们根据DateFormatter对象定义如何解释传入的日期字符串.

但是,我目前正在使用一个API,它返回date strings(yyyy-MM-dd)和datetime strings(yyyy-MM-dd HH:mm:ss),具体取决于属性.有没有办法JSONDecoder处理这个,因为提供的DateFormatter对象一次只能处理dateFormat一个?

一个火腿解决方案是重写附带的Decodable模型,只接受字符串作为其属性,并提供公共Dategetter/setter变量,但这对我来说似乎是一个糟糕的解决方案.有什么想法吗?

json-deserialization swift codable

21
推荐指数
5
解决办法
7545
查看次数

Swift Codable解码手动可选变量

我有以下代码.

import Foundation

let jsonData = """
[
    {"firstname": "Tom", "lastname": "Smith", "age": "28"},
    {"firstname": "Bob", "lastname": "Smith"}
]
""".data(using: .utf8)!

struct Person: Codable {
    let firstName, lastName: String
    let age: String?

    enum CodingKeys : String, CodingKey {
        case firstName = "firstname"
        case lastName = "lastname"
        case age
    }

    init(from decoder: Decoder) throws {
        let values = try decoder.container(keyedBy: CodingKeys.self)
        firstName = try values.decode(String.self, forKey: .firstName)
        lastName = try values.decode(String.self, forKey: .lastName)
        age = try values.decode(String.self, forKey: .age) …
Run Code Online (Sandbox Code Playgroud)

swift swift4 codable

19
推荐指数
1
解决办法
8571
查看次数

如何在Codable类型中使用Any

我目前正在处理Codable项目中的类型并遇到问题.

struct Person: Codable
{
    var id: Any
}
Run Code Online (Sandbox Code Playgroud)

id在上面的代码中可以是a String或an Int.这就是id类型的原因Any.

我知道Any不是Codable.

我需要知道的是我如何才能使它发挥作用.

ios swift codable decodable encodable

18
推荐指数
5
解决办法
1万
查看次数

协议类型不能符合协议,因为只有具体类型才能符合协议

在应用程序中,我们有两种类型的贴纸,字符串和位图。每个贴纸包可以包含这两种类型。这就是我声明模型的方式:

// Mark: - Models

protocol Sticker: Codable {
}

public struct StickerString: Sticker,  Codable, Equatable {
    let fontName: String
    let character: String
}

public struct StickerBitmap: Sticker,  Codable, Equatable {
    let imageName: String
}
Run Code Online (Sandbox Code Playgroud)

在用户选择一些贴纸并使用它们后,我们希望将这些贴纸保存到其中,UserDefaults以便我们可以向他显示“最近使用过的”贴纸选项卡。我正在尝试解码保存的[Sticker]数组:

let recentStickers = try? JSONDecoder().decode([Sticker].self, from: data)
Run Code Online (Sandbox Code Playgroud)

但我收到以下编译错误:

Protocol type 'Sticker' cannot conform to 'Decodable' because only concrete types can conform to protocols
Run Code Online (Sandbox Code Playgroud)

我不明白为什么我声明Stickeras Codablewhich 也实现了Decodable. 任何帮助将不胜感激!

protocols ios swift codable decodable

17
推荐指数
1
解决办法
3万
查看次数

Swift 4可编码阵列

所以我有一个返回JSON对象数组的API路由.例如:

[
    {"firstname": "Tom", "lastname": "Smith", "age": 31},
    {"firstname": "Bob", "lastname": "Smith", "age": 28}
]
Run Code Online (Sandbox Code Playgroud)

我试图想象如何在Swift中使用新的可编码特性将它们转换为类中的两个对象.因此,如果我有一个可编码的人类,我会想要采取这种反应并让它给我两个人物.

我也在使用Alamofire来处理这些请求.

我怎样才能做到这一点?到目前为止,我所看到的与可编码内容有关的所有内容只允许1个对象.我还没有看到任何与Alamofire或Web框架的集成.

swift swift4 codable

15
推荐指数
1
解决办法
1万
查看次数

如何使UIImage符合Codable?

Swift 4有Codable,真棒.但UIImage默认情况下不符合它.我们怎么做?

我试过singleValueContainerunkeyedContainer

extension UIImage: Codable {
  // 'required' initializer must be declared directly in class 'UIImage' (not in an extension)
  public required init(from decoder: Decoder) throws {
    let container = try decoder.singleValueContainer()
    let data = try container.decode(Data.self)
    guard let image = UIImage(data: data) else {
      throw MyError.decodingFailed
    }

    // A non-failable initializer cannot delegate to failable initializer 'init(data:)' written with 'init?'
    self.init(data: data)
  }

  public func encode(to encoder: Encoder) throws {
    var …
Run Code Online (Sandbox Code Playgroud)

uiimage swift4 codable

15
推荐指数
6
解决办法
8218
查看次数