2012-11-06 41 views
4

我知道,在4.8版本中,每個http請求都有自己的線程運行。
我正在做一個鏈接檢查器的應用程序,在while循環中做了很多http請求,我注意到在Windows任務管理器中,我的應用程序隨着時間的推移使用了超過1600個線程,並且該數字永遠不會下降,直到它崩潰了應用程序。 (我猜這就是原因。)QNetworkAccessManager線程永不完成

我的問題是,QNetworkAccessManager有沒有使用線程池的選項?
或者它有一個選項來完成它的http請求後清理它的線程嗎?

這是主要的循環:

while(!rpm_urlStack->isEmpty()) 
{ 
    QString url = rpm_urlStack->top(); 

    //define the reply 
    QNetworkReply *reply; 
    rpm_urlStack->pop(); 

    QString urlForReq(url); 

    bool returnVal = true; 
    QNetworkRequest request; 

    request.setUrl(QUrl(urlForReq)); 
    request.setRawHeader("User-Agent", USER_AGENT.toUtf8()); 
    request.setRawHeader("Accept-Charset", "ISO-8859-1,utf-8;q=0.7,*;q=0.7"); 
    request.setRawHeader("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8"); 
    request.setRawHeader("Accept-Language", "en-us,en;q=0.5"); 
    request.setRawHeader("Connection", "Keep-Alive"); 

    QEventLoop loop; 
    reply = m_networkManager->get(request); 
    connect(reply, SIGNAL(finished()), &loop, SLOT(quit())); 
    loop.exit(); 

    if(!loop.isRunning()) { 
     loop.exec(); 
    } 

    RequestFinishedHandler(reply); 

    // this is how I delete the reply object 
    delete reply; 
} 

RequestFinishedHandler(QNetworkReply *reply) 
{ 
    if (reply->error() > 0) { 
     QNetworkReply::NetworkError networkError = reply->error(); 
     QString err = reply->errorString(); 
    } else { 
     QVariant vStatusCodeV = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute); 
     QMutexLocker lock(_pMutex); // _pMutex defined as class member 
     char *buffer; 
     buffer = getCurrentDateTime(); 
     QTextStream out(m_file); 
     out << buffer << " " << _sCurrentUrl << "\n"; 
     lock.unlock(); 

     if(vStatusCodeV.toInt() == 200) { 
      QString ApiResponse; 
      QByteArray data; 
      data=reply->readAll(); 
      ApiResponse.append(QString::fromUtf8(data)); 
     } 
    } 
} 
+0

RequestFinishedHandler函數做了什麼? – didierc

+0

我更新了問題 – user63898

回答

1

appears其是有效的,該方法deleteLater必須從事件循環中調用,它必須恢復執行的控制來處理垃圾收集。

也許你應該重構你的代碼,讓事件循環代替你的while循環。或者,由於您沒有使用finished插槽來處理回覆,因此您可以直接在RequestFinishedHandler函數末尾刪除回覆。

+0

它不工作即時刪除重播對象,但線程繼續起來 – user63898

+0

請添加您對您的問題所做的更改。 – didierc

+0

我添加並更新了這個問題 – user63898