QNetworkAccessManager的异步与线程
Qt版本5.1.1
以HTTP操作为例
Qt中的HTTP操作都是异步的. 内部通过线程实现
创建线程的时机在QNetworkReplyHttpImplPrivate::postRequest()
void QNetworkReplyHttpImplPrivate::postRequest()
{
Q_Q(QNetworkReplyHttpImpl); QThread *thread = ;
if (synchronous) {
// A synchronous HTTP request uses its own thread
thread = new QThread();
thread->setObjectName(QStringLiteral("Qt HTTP synchronous thread"));
QObject::connect(thread, SIGNAL(finished()), thread, SLOT(deleteLater()));
thread->start();
} else if (!managerPrivate->httpThread) {
// We use the manager-global thread.
// At some point we could switch to having multiple threads if it makes sense.
managerPrivate->httpThread = new QThread();
managerPrivate->httpThread->setObjectName(QStringLiteral("Qt HTTP thread"));
managerPrivate->httpThread->start(); thread = managerPrivate->httpThread;
} else {
// Asynchronous request, thread already exists
thread = managerPrivate->httpThread;
} .......... // Move the delegate to the http thread
delegate->moveToThread(thread);
// This call automatically moves the uploadDevice too for the asynchronous case. ...........
}
分为两种情况:
(1) synchronous == true 每次HTTP请求创建自己的线程, 并在finished后自动退出线程
在QNetworkRequest设置QNetworkRequest::SynchronousRequestAttribute 属性为真时, synchronous = true, 然而SynchronousRequestAttribute被Qt标记为internal. 以防止外部创建synchronous HTTP请求.
我在Qt的源码中找到一点说明, QNetworkReplyHttpImpl的构造函数中.
........
// Internal code that does a HTTP reply for the synchronous Ajax
// in Qt WebKit.
QVariant synchronousHttpAttribute = request.attribute(
static_cast<QNetworkRequest::Attribute>(QNetworkRequest::SynchronousRequestAttribute));
if (synchronousHttpAttribute.isValid()) {
d->synchronous = synchronousHttpAttribute.toBool();
........
webkit的ajax请求使用
(2) synchronous == false 则把所有http请求放置在一个线程中.
并且该线程在
QNetworkAccessManagerPrivate对象析构(即QNetworkAccessManager析构)或者调用QNetworkAccessManagerPrivate::clearCache 时退出
QNetworkAccessManagerPrivate::~QNetworkAccessManagerPrivate()
{
if (httpThread) {
httpThread->quit();
httpThread->wait();
if (httpThread->isFinished())
delete httpThread;
else
QObject::connect(httpThread, SIGNAL(finished()), httpThread, SLOT(deleteLater()));
httpThread = ;
}
} void QNetworkAccessManagerPrivate::clearCache(QNetworkAccessManager *manager)
{
manager->d_func()->objectCache.clear();
manager->d_func()->authenticationManager->clearCache(); if (manager->d_func()->httpThread) {
manager->d_func()->httpThread->quit();
manager->d_func()->httpThread->wait();
if (manager->d_func()->httpThread->isFinished())
delete manager->d_func()->httpThread;
else
QObject::connect(manager->d_func()->httpThread, SIGNAL(finished()), manager->d_func()->httpThread, SLOT(deleteLater()));
manager->d_func()->httpThread = ;
}
}
否则会一直HTTP 线程会一直存在. 另外, 每个QNetworkAccessManager对象对应自己的HTTP thread.
QNetworkAccessManager的异步与线程的更多相关文章
- Handler 、 Looper 、Message异步消息处理线程机制( hander消息机制原理)
Handler . Looper .Message 这三者都与Android异步消息处理线程相关的概念. 那么什么叫异步消息处理线程呢? 异步消息处理线程启动后会进入一个无限的循环体之中,每循环一次, ...
- JDK 伪异步编程(线程池)
伪异步IO编程 BIO主要的问题在于每当有一个新的客户端请求接入时,服务端必须创建一个新的线程处理新接入的客户端链路,一个线程只能处理一个客户端连接.在高性能服务器应用领域,往往需要面向成千上万个客户 ...
- 14.并发与异步 - 1.线程处理Thread -《果壳中的c#》
14.2.1 创建一个线程 实例化一个Thread对象,然后调用它的Start方法,就可以创建和启动一个新的线程.最简单的Thread构造方法是接受一个ThreadStart代理:一个无参方法,表示执 ...
- Java异步、线程池解决方案
一.ThreadPoolExecutor------线程池 private static final ThreadPoolExecutor threadPoolExecutor = new Threa ...
- JAVA并行异步编程,线程池+FutureTask
java 在JDK1.5中引入一个新的并发包java.util.concurrent 该包专门为java处理并发而书写. 在java中熟悉的使用多线程的方式为两种?继续Thread类,实现Runnal ...
- .NET 同步与异步 之 线程安全的集合 (十一)
本随笔续接:.NET 同步与异步 之 警惕闭包(十) 无论之前说的锁.原子操作 还是 警惕闭包,都是为安全保驾护航,本篇随笔继续安全方面的主题:线程安全的集合. 先看一下命名空间:System.Col ...
- Django异步任务线程池
当数据库数据量很大时(百万级),许多批量数据修改请求的响应会非常慢,一些不需要即时响应的任务可以放到后台的异步线程中完成,发起异步任务的请求就可以立即响应 选择用线程池的原因是:线程比进程更为可控.不 ...
- SpringBoot异步及线程池配置
异步方法注解@Async 在SpringBoot中进行异步处理,可以使用异步注解@Async和@EnableAsync. @Async注解表示异步,如:@Async("asyncServic ...
- 进程?线程?多线程?同步?异步?守护线程?非守护线程(用户线程)?线程的几种状态?多线程中的方法join()?
1.进程?线程?多线程? 进程就是正在运行的程序,他是线程的集合. 线程是正在独立运行的一条执行路径. 多线程是为了提高程序的执行效率.2.同步?异步? 同步: 单线程 异步: 多线程 3.守护线程? ...
随机推荐
- Mongoose:Schema之路
说明:本文在个人博客地址为edwardesire.com,欢迎前来品尝. Mongoose学习 这里的Mongoose当然不是图片上的萌物,它是一个MongoDB对象建模工具(object model ...
- -exec 与 xargs 的区别
实地在shell里执行下如下命令就知道区别了: $ find -type f -exec echo {} \; 很明显,exec是对每个找到的文件执行一次命令.从这里可以看出exec的缺点是每处理一个 ...
- http://www.hameister.org/JavaFX_PuzzleGame.html
http://www.hameister.org/JavaFX_PuzzleGame.html
- [iOS 多线程 & 网络 - 2.3] - 解析xml
A.XML基本知识 1.xml概念 什么是XML全称是Extensible Markup Language,译作“可扩展标记语言”跟JSON一样,也是常用的一种用于交互的数据格式一般也叫XML文档(X ...
- 分析nginx access log日志的命令
统计访问最多的ip 1. tail -n 10000 xxaccess_log | cut -d " " -f 1 |sort|uniq -c|sort -rn|head -10 ...
- OpenCDN2.0安装
部署说明 为网站加速,建立私有的CDN节点群,每部署一个CDN节点只需5分钟,无节点数量上限!参考 http://ocdn.me/ 安装需求 OpenCDN的Beta版目前在CentOS5.x - C ...
- Codeforces Round #271 (Div. 2) F. Ant colony (RMQ or 线段树)
题目链接:http://codeforces.com/contest/474/problem/F 题意简而言之就是问你区间l到r之间有多少个数能整除区间内除了这个数的其他的数,然后区间长度减去数的个数 ...
- [html]html常用代码
上传文件表单属性 enctype="multipart/form-data" 单选(是否选中) checked="checked" 下拉列表(是否选中) sel ...
- MFC中常用的内容
在程序中更改静态文本内容. GetDlgItem(IDC_STATIC)->SetWindowText("欢迎"); 不用UpdateData(false); 如果提示con ...
- 【LINUX】编程笔记
a storage class can only be specified for objects and functions extern修饰一个struct报错,错误原因如上,C++中存储类修 ...