2016-05-14 122 views
3

我在做什麼錯?在此先感謝您的幫助!!爲什麼我會收到UnsafeMutablePointer錯誤?

我寫了下面的代碼,目的是控制對我的數據庫的請求,還有一個外部網站,我試圖解析其數據,以便填充我的數據庫。目標是生成1000多個請求,將它們放在堆棧上,然後限制在給定時間內同時發送多少個請求。它工作得很好,但每隔一段時間,它此行的代碼生成異常:

RequestManager.requests .append(!_request)

這行代碼是Push功能WebRequestManager。你可以看到下面的代碼。

致命錯誤:UnsafeMutablePointer.destroy負計數

一個例子請求如下所示:

WebRequestManager.Request(WebRequest(_data: self.beerstores, _url: "http://brewskibooze.com/beerstore/build_database/postbeerstoreproductavailability.php"), 
            completion: { 
             (data,response,error) in 
             if error == nil 
             { 
              self.display(_string: "Process Complete") 
             } 
             else 
             { 
              self.display(_string: "Unable to post inventory.") 
             } 


            }) 

下面的代碼:

class WebRequest 

{

private var trials = 0 

private var executed = false 

private var data : AnyObject? 

private var url : String? 

private var completion : ((data: NSData?, response: NSURLResponse?, error : ErrorType?) -> Void)? 

private func execute() 
{ 
    if !executed 
    { 
     trials += 1 
     self.executed = true 
     let endpoint = NSURL(string: url!) 

     if (endpoint == nil) { return } 

     let request = NSMutableURLRequest(URL: endpoint!) 

     if data != nil 
     { 
      if data is NSData 
      { 
       request.HTTPMethod = "POST" 
       request.HTTPBody = data as? NSData 
      } 
      else 
      { 
       request.HTTPMethod = "POST" 
       request.HTTPBody = try! NSJSONSerialization.dataWithJSONObject(data!, options: []) 
      } 
     } 
     request.addValue("application/json", forHTTPHeaderField: "Content-Type") 
     request.addValue("application/json", forHTTPHeaderField: "Accept") 

     let task = NSURLSession.sharedSession().dataTaskWithRequest(request) 
     { 
      data, response, error in 

      if error == nil 
      { 

       WebRequestManager.pop() 

       self.completion?(data: data,response: response,error: error) 
      } 
      else 
      { 
       if self.trials < 10 
       { 
        self.executed = false 
        self.execute() 
       } 
       else 
       { 
        WebRequestManager.pop() 
        self.completion?(data: data,response: response,error: error) 
       } 
      } 
     } 
     task.resume() 
    } 
} 

init(_query : Query?) 
{ 

    data = _query!.data 

    url = _query!.toString() 
} 

init(_data : AnyObject?, _url : String) 
{ 

    data = _data 

    url = _url 
} 

init(_data : NSData?, _url : String) 
{ 
    data = _data 
    url = _url 
} 

deinit 
{ 
    completion = nil 
    data = nil 
    url = nil 
} 

}

class WebRequestManager 

{

private var requests : [WebRequest]? 
private static var MaxConcurrentRequests = 10 

private var currentRequestCount = 0 

private static var RequestManager = WebRequestManager() 

private class var RequestCount : Int 
{ 
    return RequestManager.currentRequestCount 
} 

private class func DecrementCount() 
{ 
    RequestManager.currentRequestCount -= 1 
} 

private class func IncrementCount() 
{ 
    RequestManager.currentRequestCount += 1 
} 

private class func push(_request : WebRequest?) 
{ 
    if _request != nil 
    { 
     IncrementCount() 
     RequestManager.requests?.append(_request!) 
    } 

} 

private class func pop() 
{ 
    if RequestManager.requests?.count > 0 
    { 
     let last : WebRequest? = RequestManager.requests?.removeLast() 
     if last != nil 
     { 
      last!.execute() 
      DecrementCount() 
     } 
    } 
} 

init() 
{ 
    requests = [WebRequest]() 
} 

class var ActiveThreadCount : Int 
{ 
    return RequestManager.currentRequestCount 
} 


class func Request(_request : WebRequest?,completion : ((data: NSData?, response: NSURLResponse?, error : ErrorType?) -> Void)?) 
{ 
    _request?.completion = completion 
    if RequestCount < MaxConcurrentRequests 
    { 
     _request?.execute() 
    } 
    push(_request) 
} 

}

+0

這行做了Debuger停止?而你的代碼太長了...... – Lumialxk

+0

對不起,關於長碼。我試圖徹底描述這個問題。它在WebRequestManager RequestManager.requests?.append(_request!)的push()函數中退出 – bhardy

+0

有多個請求涉及推送和彈出,我會發現自己處於同時彈出和推送的位置,這可能嗎?我將如何解決這個問題? – bhardy

回答

0

我敢肯定,我剛纔已經回答我的問題。問題在於,在線程環境中,所有這些請求以及許多請求和彈出請求都會導致同時彈出和推送的風險。該解決方案似乎是這樣的:

objc_sync_enter(鎖定)

objc_sync_exit(鎖定)

信貸由於在這裏:​​

Create thread safe array in swift

但是,導致此警告...

| synchronize-skip |在快照塊內啓動了一個柵欄 - 跳過了工作空間同步,因爲它可能會使fenceExemptQueue中的消息出列,並且快照預計不會發生 2016-05-14 14:11:57.791 _____ [348:99565] | synchronize -skip |籬笆開始快照塊內 - 跳過工作區同步,因爲它可能離隊從fenceExemptQueue信息和快照預計不會發生

0

您指出我在正確的方向,串行調度隊列解決了我的問題沒有警告。

創建快捷3串行調度隊列:

let serialQueue = DispatchQueue(label: "myqueue")` 

然後修改數組中的隊列:

serialQueue.sync { 
     //modify array 
    } 
相關問題