Я знаю, что в версии 4.8 для каждого http-запроса запускается собственный поток.
Я делаю приложение для проверки ссылок, которое выполняет много http-запросов в цикле, и я замечаю в диспетчере задач Windows, что мое приложение использует более 1600 потоков с течением времени, и число никогда не уменьшается, только до тех пор, пока оно не падает приложение. (Я предполагаю, что это причина.)
Мой вопрос, делает ли 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));
}
}
}
Это появляется чтобы быть эффективным, deleteLater
метод должен вызываться из цикла событий, который должен восстановить контроль над выполнением для обработки сборки мусора.
Возможно, вам следует реорганизовать свой код, чтобы цикл обработки событий заменил цикл while. В качестве альтернативы, так как вы не используете finished
слот для обработки ответа, возможно, вы можете удалить ответ непосредственно в конце RequestFinishedHandler
функция.
Других решений пока нет …