草庐IT

ios - swift 4 可编码 : Converting JSON return String to Int/Date/Float

coder 2023-07-17 原文

我正在研究一些项目并删除 JSON 解析框架,因为使用 Swift 4 似乎很简单。我遇到了这个奇怪的 JSON 返回,其中 IntsDates 作为 Strings 返回。

我看了GrokSwift's Parsing JSON with Swift 4 , Apple's website ,但我没有看到任何关于 re: changing types 的内容。

Apple's example code显示了如何更改 key 名称,但我很难弄清楚如何更改 key 类型。

这是它的样子:

{
    "WaitTimes": [
        {
            "CheckpointIndex": "1",
            "WaitTime": "1",
            "Created_Datetime": "10/17/2017 6:57:29 PM"
        },
        {
            "CheckpointIndex": "2",
            "WaitTime": "6",
            "Created_Datetime": "10/12/2017 12:28:47 PM"
        },
        {
            "CheckpointIndex": "0",
            "WaitTime": "8",
            "Created_Datetime": "9/26/2017 5:04:42 AM"
        }
    ]
}

我使用 CodingKey 将字典键重命名为符合 Swift 的条目,如下所示:

struct WaitTimeContainer: Codable {
  let waitTimes: [WaitTime]

  private enum CodingKeys: String, CodingKey {
    case waitTimes = "WaitTimes"
  }

  struct WaitTime: Codable {
    let checkpointIndex: String
    let waitTime: String
    let createdDateTime: String

    private enum CodingKeys: String, CodingKey {
      case checkpointIndex = "CheckpointIndex"
      case waitTime = "WaitTime"
      case createdDateTime = "Created_Datetime"
    }
  }
}

这仍然给我留下了 String,它应该是 IntDate。我将如何使用可编码协议(protocol)?

最佳答案

这是 not yet possible因为 Swift 团队在 JSONDecoder 中只提供了 String to date 解码器。

不过您始终可以手动解码:

struct WaitTimeContainer: Decodable {
    let waitTimes: [WaitTime]

    private enum CodingKeys: String, CodingKey {
        case waitTimes = "WaitTimes"
    }

    struct WaitTime:Decodable {
        let checkpointIndex: Int
        let waitTime: Float
        let createdDateTime: Date

        init(checkpointIndex: Int, waitTime: Float, createdDateTime:Date) {
            self.checkpointIndex = checkpointIndex
            self.waitTime = waitTime
            self.createdDateTime = createdDateTime
        }

        static let formatter: DateFormatter = {
            let formatter = DateFormatter()
            formatter.calendar = Calendar(identifier: .iso8601)
            formatter.locale = Locale(identifier: "en_US_POSIX")
            formatter.timeZone = TimeZone(secondsFromGMT: 0)
            formatter.dateFormat = "MM/dd/yyyy hh:mm:ss a"
            return formatter
        }()

        init(from decoder: Decoder) throws {
            let container = try decoder.container(keyedBy: CodingKeys.self)
            let checkpointIndexString = try container.decode(String.self, forKey: .checkpointIndex)
            let checkpointIndex = Int(checkpointIndexString)!

            let waitTimeString = try container.decode(String.self, forKey: .waitTime)
            let waitTime = Float(waitTimeString)!

            let createdDateTimeString =  try container.decode(String.self, forKey: .createdDateTime)

            let createdDateTime = WaitTime.formatter.date(from: createdDateTimeString)!

            self.init(checkpointIndex:checkpointIndex, waitTime:waitTime, createdDateTime:createdDateTime)
        }

        private enum CodingKeys: String, CodingKey {
            case checkpointIndex = "CheckpointIndex"
            case waitTime = "WaitTime"
            case createdDateTime = "Created_Datetime"
        }
    }
}

关于ios - swift 4 可编码 : Converting JSON return String to Int/Date/Float,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46901445/

有关ios - swift 4 可编码 : Converting JSON return String to Int/Date/Float的更多相关文章

  1. ruby-on-rails - date_field_tag,如何设置默认日期? [ rails 上的 ruby ] - 2

    我想设置一个默认日期,例如实际日期,我该如何设置?还有如何在组合框中设置默认值顺便问一下,date_field_tag和date_field之间有什么区别? 最佳答案 试试这个:将默认日期作为第二个参数传递。youcorrectlysetthedefaultvalueofcomboboxasshowninyourquestion. 关于ruby-on-rails-date_field_tag,如何设置默认日期?[rails上的ruby],我们在StackOverflow上找到一个类似的问

  2. ruby - 如何验证 IO.copy_stream 是否成功 - 2

    这里有一个很好的答案解释了如何在Ruby中下载文件而不将其加载到内存中:https://stackoverflow.com/a/29743394/4852737require'open-uri'download=open('http://example.com/image.png')IO.copy_stream(download,'~/image.png')我如何验证下载文件的IO.copy_stream调用是否真的成功——这意味着下载的文件与我打算下载的文件完全相同,而不是下载一半的损坏文件?documentation说IO.copy_stream返回它复制的字节数,但是当我还没有下

  3. Ruby 文件 IO 定界符? - 2

    我正在尝试解析一个文本文件,该文件每行包含可变数量的单词和数字,如下所示:foo4.500bar3.001.33foobar如何读取由空格而不是换行符分隔的文件?有什么方法可以设置File("file.txt").foreach方法以使用空格而不是换行符作为分隔符? 最佳答案 接受的答案将slurp文件,这可能是大文本文件的问题。更好的解决方案是IO.foreach.它是惯用的,将按字符流式传输文件:File.foreach(filename,""){|string|putsstring}包含“thisisanexample”结果的

  4. Get https://registry-1.docker.io/v2/: net/http: request canceled while waiting - 2

    1.错误信息:Errorresponsefromdaemon:Gethttps://registry-1.docker.io/v2/:net/http:requestcanceledwhilewaitingforconnection(Client.Timeoutexceededwhileawaitingheaders)或者:Errorresponsefromdaemon:Gethttps://registry-1.docker.io/v2/:net/http:TLShandshaketimeout2.报错原因:docker使用的镜像网址默认为国外,下载容易超时,需要修改成国内镜像地址(首先阿里

  5. ruby - 为什么不能使用类IO的实例方法noecho? - 2

    print"Enteryourpassword:"pass=STDIN.noecho(&:gets)puts"Yourpasswordis#{pass}!"输出:Enteryourpassword:input.rb:2:in`':undefinedmethod`noecho'for#>(NoMethodError) 最佳答案 一开始require'io/console'后来的Ruby1.9.3 关于ruby-为什么不能使用类IO的实例方法noecho?,我们在StackOverflow上

  6. ruby - Rails 3 - 我可以将开始日期设置为 date_select 方法吗? - 2

    date_select方法只能设置:start_year,但我想设置开始日期(例如3个月前的日期)(但没有这样的选项)。那么,我可以将开始日期设置为date_select方法吗?或者,要制作这样的选择框,我应该使用select_tag和options_for_select吗?或者,有什么解决办法吗?谢谢, 最佳答案 有可能……例如:start_year–设置年份选择的开始年份。默认为Time.now.year-5参见thisresource. 关于ruby-Rails3-我可以将开始日期

  7. ruby - Date 与 nil 的比较失败 - ruby - 2

    我正在运行这样的代码:ifvalid_from>Date.today当我运行它时,我得到一个错误提示comparisonofDatewithnilfailed我假设它正在发生,因为在某些情况下valid_from是nil。有没有办法避免出现此错误? 最佳答案 你可以这样做:ifvalid_fromandvalid_from>Date.today...end这将在第一个子句上短路,因为valid_from为nil,因此为false。 关于ruby-Date与nil的比较失败-ruby,我们

  8. ruby-on-rails - 32651 :ERROR comparison of Float with Float failed ruby - 2

    我是Rails的新手,我遇到了一个错误,但我似乎找不到问题所在。这是日志:[32651:ERROR]2012-10-0913:46:52::comparisonofFloatwithFloatfailed[32651:ERROR]2012-10-0913:46:52::/home/sunny/backend/lib/analytics/lifetime.rb:45:in`each'/home/sunny/backend/lib/analytics/lifetime.rb:45:in`max'/home/sunny/backend/lib/analytics/lifetime.rb:45

  9. ruby - 为什么在 Ruby 中是 Float::INFINITY == Float::INFINITY? - 2

    在数学中,2个无穷大既不等于,也不大于或小于then。那么是什么给了?在irb中,Float::INFINITY==Float::INFINITY(在ruby​​1.9.3中测试) 最佳答案 用更专业的术语来说,这一切都归结为浮点运算的IEEE754标准。TheIEEE754standarddoesimplicitlydefineInfinity==Infinitytobetrue.Therelevantpartofthestandardissection5.7:"Fourmutuallyexclusiverelationsarep

  10. ruby - 强制 Ruby 不以标准形式/科学记数法/指数记数法输出 float - 2

    我遇到了同样的问题here对于python,但对于ruby​​。我需要输出这样一个小数字:0.00001,而不是1e-5。有关我的特定问题的更多信息,我正在使用f.write("Mynumber:"+small_number.to_s+"\n")输出到一个文件对于我的问题,准确性不是什么大问题,所以只做一个if语句来检查是否small_number那么更通用的方法是什么? 最佳答案 f.printf"Mynumber:%.5f\n",small_number您可以将.5(小数点右侧5位数字)替换为您喜欢的任何特定格式大小,例如,%8

随机推荐