Swift:如何让Alamofire逐个获得请求

Tal*_*han 6 arrays asynchronous swift alamofire

我是swift的初学者,我遇到过需要在循环中运行AlamoFire GET请求的情况.但据我所知,Alamofire Get请求是一个异步调用,并在循环中调用它将创建许多线程.

要求是:

  1. 我有一系列的网址
  2. 必须在循环中遍历数组

  3. 必须通过AlamoFire GET请求调用每个索引上的URL

  4. 通过请求接收的数据将被添加到数据数组中

  5. 将最后一个数据保存在数组中后,应调用CollectionView.reload调用

伪代码如下:

    for bookmarkURL in bookmarks
        Alamofire.request(.GET, bookmarkURL ).responseJSON
                { response in switch response.result {
                case .Success(let JSON):
                    x[i] = JSON as! [String : AnyObject] // saving data

                case .Failure(let error):
                     print("the error for \(self.bookmarkURL) is \(error) ")
                }
        i++
        if i == bookmarks.count{
           collectionView.reload()
          break}
}
Run Code Online (Sandbox Code Playgroud)

谁能告诉我怎么按顺序做呢?

Roh*_*nap 11

  • bookmarks数组作为类属性.
  • 在遍历数组时添加一个类属性index来存储索引值(Int)bookmarks
  • 添加一个函数来进行API调用并递归调用它.

这是代码:

func getData() {
    var x = [[String: AnyObject]]()
    Alamofire.request(.GET, bookmarks[index]).responseJSON { response in
        switch response.result {
        case .Success(let JSON):
            x[self.index] = JSON as! [String : AnyObject] // saving data
            self.index = self.index + 1
            if self.index < self.bookmarks.count {
                self.getData()
            }else {
                self.collectionView.reloadData()
            }
        case .Failure(let error):
            print("the error for \(self.bookmarks[self.index]) is \(error) ")
            if self.index < self.bookmarks.count {
                self.getData()
            }else {
                self.collectionView.reloadData()
            }
        }
    }

}
Run Code Online (Sandbox Code Playgroud)

这样,您的请求将仅在前一个完成后进行,从而使其顺序而不是并行,您也可以仅在最后一个请求完成后重新加载collectionView.


Joh*_*tty 5

如果您只想在收到全部数据后重新加载您的集合视图,您可以使用dispatch_group类似,

    let group = dispatch_group_create() // create a group.

    dispatch_group_enter(group) // enter the group just before create the request 

    dispatch_group_leave(group)//leave the group on completion closure
    dispatch_group_notify(group, group) { 
        //reload your collection view 
    }
Run Code Online (Sandbox Code Playgroud)

完整代码

    for bookmarkURL in bookmarks {
        dispatch_group_enter(group)
        Alamofire.request(.GET, bookmarkURL ).responseJSON { response in 
        switch response.result {
            case .Success(let JSON):
                x[i] = JSON as! [String : AnyObject] // saving data

            case .Failure(let error):
                print("the error for \(self.bookmarkURL) is \(error) ")
            }
        dispatch_group_leave(group)
        }
    }
    dispatch_group_notify(group, group) {
         collectionView.reload()
    }
Run Code Online (Sandbox Code Playgroud)

注意:如果您的书签数组太大,最好不要循环进行。为此,您可以使用以下代码

func loadBookmarkAtIndex(index: Int) {
    if index >= bookmarks.count {
        collectionView.reload()
        return
    }
    let bookmarkURL = bookmarks[index]
    Alamofire.request(.GET, bookmarkURL ).responseJSON { response in

        switch response.result {
        case .Success(let JSON):
            x[index] = JSON as! [String : AnyObject] // saving data

        case .Failure(let error):
            print("the error for \(bookmarkURL) is \(error) ")

        }
        self.loadBookmarkAtIndex(index+1)
    }
}
Run Code Online (Sandbox Code Playgroud)

self.loadBookmarkAtIndex(0)从您启动数据检索的位置调用。