关于数组:使用swift进行JSON数据循环

For loop in JSON data using swift

我正在分析JSON数据并迭代结果,一切都很好。但我需要一种方法来控制循环中的迭代次数。例如,只获取前10个结果。

这里我分析JSON天气数据状态图标。我只想得到前10个结果并将它们附加到数组中。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
if let list = arrayList["weather"] as? [[String : AnyObject]]{

  for arrayList in list{

     if let iconString = arrayList["icon"] as? String{
        if let url = NSURL(string:"http://openweathermap.org/img/w/\(iconString).png"){
           let iconImgData = NSData(contentsOfURL: url)
           let image = UIImage(data: iconImgData!)
           self.forcastImg.append(image!)                                                                  self.forcastView.reloadData()

                    }
              }
         //print(list)
     }
  }


有很多方法可以做到这一点。

如您所建议的,您可以手动控制循环以运行前n个元素:

1
2
3
4
5
6
7
if let list = arrayList["weather"] as? [[String : AnyObject]] {

   for i in 0 ..< 10 {
      let arrayList = list[i]
      // Do stuff with arrayList
   }
}

如果知道数组的长度至少为10,则可以使用Cristik在其注释中建议的arrayslice语法:

1
2
3
4
5
6
if let list = arrayList["weather"] as? [[String : AnyObject]] where list.count > 10 {
   let firstTenResults = list[0 ..< 10]
   for arrayList in firstTenResults {
      // Do stuff with arrayList
   }
}

不过,prefix(_:)方法可能是最清晰的。此方法的优点是,如果您提供的参数大于数组的长度,它将返回您拥有的元素,而不会引发错误:

1
2
3
4
5
6
if let list = arrayList["weather"] as? [[String : AnyObject]] {
   let firstTenResults = list.prefix(10)
   for arrayList in firstTenResults {
      // Do stuff with arrayList
   }
}


以下是一个非常迅速的解决方案:

1
2
3
4
5
6
7
8
9
10
11
let first10Images = (arrayList["weather"] as? [[String : AnyObject]])?.reduce((0, [UIImage]())) {
    guard $0.0.0 < 10,
        let iconString = $0.1["icon"] as? String,
        url = NSURL(string:"http://openweathermap.org/img/w/\(iconString).png"),
        iconImgData = NSData(contentsOfURL: url),
        image = UIImage(data: iconImgData)
        else {
            return $0.0
    }
    return ($0.0.0 + 1, $0.0.1 + [image])
}.1

基本上,通过使用由计数器和结果数组组成的一对来减少weather数组。如果计数器超过10,或者您无法下载图像,您只需返回累积值移到下一个项目,否则您将增加计数器并追加下载的图像。

注意,您会得到一个可选的,因为第一个强制转换可能会失败。不过,我相信您不会对此有任何问题,从发布的代码来看,您知道如何处理选项:)