隐式共享
Qt的许多类使用隐式数据共享, 最大限度提高资源使用率, 减少复制. 函数传参时, 隐式共享只传递数据指针, 既安全又高效, 并且只有函数往变量写入数据时, 数据才会复制, 即., 写时复制.
概述
共享类包含指向共享数据库的指针, 这个数据块包含引用计数和数据.
创建共享对象时, 引用计数设置为1. 有新对象引用共享数据时, 引用计数增加. 当对象取消引用共享数据时, 引用计数减少. 引用计数为0时, 删除共享数据.
处理共享对象时, 有两种方法复制对象. 我们通常讨论深拷贝和浅拷贝. 深拷贝表示复制对象. 浅拷贝是一种引用复制, 即. 指向共享数据的指针. 对于内存和CPU而言, 深拷贝代价可能很高. 浅拷贝非常快, 因为它只涉及指针复制和引用计数.
隐式共享对象的对象分配采用浅拷贝.
隐式共享的好处是程序不需要进行不必要的数据复制, 这样可以降低内存的使用率, 减少数据复制. 对象容器分配, 作为函数参数传递, 作为函数返回值.
隐式共享发生在后台; 程序员不需要担心这个事情. 然而, Qt的容器迭代器与STL的不同. 阅读 Implicit sharing iterator problem.
在多线程应用程序中, 也会隐式共享, 参见 Threads and Implicitly Shared Classes.
使用 QSharedData 和 QSharedDataPointer 自定义隐式共享类.
隐式共享的细节
如果对象即将改变, 且引用计数大于1, 则隐式共享自动将对象与共享块分离. (这通常被称为 写时复制 或 值语义.)
隐式共享类控制内部数据. 在任何修改数据的成员函数中, 它必须在修改数据之前自动分离数据. 注意: 隐式对象的容器迭代器必须考虑; 参见 Implicit sharing iterator problem.
QPen 使用隐式共享, 所有的成员函数在改变内部数据之前会分离共享数据.
Code fragment:
void QPen::setStyle(Qt::PenStyle style) { detach(); // detach from common data d->style = style; // set the style member } void QPen::detach() { if (d->ref != 1) { ... // perform a deep copy } }
类列表
下表列出的类在修改对象时, 自动分离公共数据. 开发人员甚至不会注意到这些对象是共享的. 因此, 你应该将它们的单独实例视为独立对象. 除非共享数据, 它们始终表现的跟独立对象一样. 因此, 你可以将这些类作为函数参数, 不必担心复制开销.
示例:
QPixmap p1, p2; p1.load("image.bmp"); p2 = p1; // p1 and p2 share data QPainter paint; paint.begin(&p2); // cuts p2 loose from p1 paint.drawText(0,50, "Hi"); paint.end();
上述示例中, p1
和 p2
在调用 QPainter::begin() 之前共享数据, 绘制修改图片.
警告: 使用STL风格迭代器时, 复制共享容器必须小心 (QMap, QVector等). 参见 Implicit sharing iterator problem.
Output stream for debugging information | |
Access to directory structures and their contents | |
System-independent file information | |
Holds the environment variables that can be passed to a program | |
Provides information about currently mounted storage and drives | |
Convenient interface for working with URLs | |
Way to manipulate a key-value pairs in a URL's query | |
Used to locate data in a data model | |
Encapsulates a JSON array | |
Way to read and write JSON documents | |
Used to report errors during JSON parsing | |
Encapsulates a JSON object | |
Encapsulates a value in JSON | |
Acts like a union for the most common Qt data types | |
Describes types of file or data, represented by a MIME type string | |
Array of bits | |
Array of bytes | |
List of byte arrays | |
Template class that provides a cache | |
Compares strings according to a localized collation algorithm | |
Can be used to speed up string collation | |
Defines a possible command-line option | |
Template class that provides a contiguous cache | |
Date and time functions | |
Template class that provides a hash-table-based dictionary | |
Convenience QHash subclass that provides multi-valued hashes | |
Template class that provides linked lists | |
Template class that provides lists | |
Converts between numbers and their string representations in various languages | |
Template class that provides a red-black-tree-based dictionary | |
Convenience QMap subclass that provides multi-valued maps | |
Generic container that provides a queue | |
Pattern matching using regular expressions | |
Pattern matching using regular expressions | |
The results of a matching a QRegularExpression against a string | |
Iterator on the results of a global match of a QRegularExpression object against a string | |
Template class that provides a hash-table-based set | |
Template class that provides a stack | |
Unicode character string | |
List of strings | |
Way of finding Unicode text boundaries in a string | |
Template class that provides a dynamic array | |
Refers to one pending asynchronous call | |
Holds one Unix file descriptor | |
Monochrome (1-bit depth) pixmaps | |
Scalable icons in different modes and states | |
Hardware-independent image representation that allows direct access to the pixel data, and can be used as a paint device | |
Paint device that records and replays QPainter commands | |
Off-screen image representation that can be used as a paint device | |
Mouse cursor with an arbitrary shape | |
Encapsulates a key sequence as used by shortcuts | |
Contains color groups for each widget state | |
Wraps an OpenGL debug message | |
Defines the fill pattern of shapes drawn by QPainter | |
Used in combination with QBrush to specify gradient fills | |
Container for painting operations, enabling graphical shapes to be constructed and reused | |
Defines how a QPainter should draw lines and outlines of shapes | |
Vector of points using integer precision | |
Vector of points using floating point precision | |
Specifies a clip region for a painter | |
Specifies a font used for drawing text | |
General information about fonts | |
Font metrics information | |
Font metrics information | |
Direct access to the internal glyphs in a font | |
Access to a single physical instance of a font | |
Enables optimized drawing of text when the text and its layout is updated rarely | |
Offers an API to access and modify QTextDocuments | |
Represents a piece of formatted text from a QTextDocument | |
Formatting information for blocks of text in a QTextDocument | |
Formatting information for characters in a QTextDocument | |
Formatting information for a QTextDocument | |
Formatting information for frames in a QTextDocument | |
Formatting information for images in a QTextDocument | |
Formatting information for lists in a QTextDocument | |
Formatting information for table cells in a QTextDocument | |
Formatting information for tables in a QTextDocument | |
Cache information | |
Holds a body part to be used inside a HTTP multipart MIME message | |
Holds one network cookie | |
Holds a request to be sent with QNetworkAccessManager | |
Abstraction of one or more access point configurations | |
Stores information about a domain name record | |
Stores information about a host address record | |
Stores information about a DNS MX record | |
Stores information about a DNS SRV record | |
Stores information about a DNS TXT record | |
IP address | |
Stores one IP address supported by a network interface, along with its associated netmask and broadcast address | |
Listing of the host's IP addresses and network interfaces | |
Network layer proxy | |
Used to query the proxy settings for a socket | |
Convenient API for an X509 certificate | |
API for accessing the extensions of an X509 certificate | |
Represents an SSL cryptographic cipher | |
Holds the configuration and state of an SSL connection | |
Interface for Diffie-Hellman parameters for servers | |
SSL error | |
Interface for private and public keys | |
Authentication data for pre shared keys (PSK) ciphersuites |