Qt Implicit Sharing (隐式共享)

今天翻译了以下Qt文档中关于隐式共享的叙述,在此记录下来供以后查看。由于我水平有限(英语四级依然没过),所以大家谨慎参考。如有高手请指正其中错误,谢谢

Implicit Sharing
隐式共享

Many C++ classes in Qt use implicit data sharing to maximize resource usage and minimize copying. Implicitly shared classes are both safe and efficient when passed as arguments, because only a pointer to the data is passed around, and the data is copied only if and when a function writes to it, i.e., copy-on-write.

Qt中的很多C++类通过使用隐式数据共享来最大化资源的使用效率和最小化复制的资源耗费。将隐
式共享类作为参数传递不仅安全而且效率高,因为在这个过程中只有指向这个数据的指针被传递,
并且当且仅当有函数对这个数据进行写操作时,才会对该数据进行复制。

Overview
Implicit Sharing in Detail
List of Classes
Overview

A shared class consists of a pointer to a shared data block that contains a reference count and the data.

一个共享类包括一个指向一个共享数据块的指针,共享数据块由数据和对共享数据进行引用的数目。

When a shared object is created, it sets the reference count to 1. The reference count is incremented whenever a new object references the shared data, and decremented when the object dereferences the shared data. The shared data is deleted when the reference count becomes zero.

当一个共享对象被创建时,共享数据的引用数目会被设置为1.无论何时,只要有一个新的对象引用该
共享数据,该共享数据对应的这个引用数目都会加一,相反,若有对象不再引用该共享数据时,其对
应的引用数目将会减一。当共享数据的引用数目为0时,该共享数据就会被撤销掉。

When dealing with shared objects, there are two ways of copying an object. We usually speak about deep and shallow copies. A deep copy implies duplicating an object. A shallow copy is a reference copy, i.e. just a pointer to a shared data block. Making a deep copy can be expensive in terms of memory and CPU. Making a shallow copy is very fast, because it only involves setting a pointer and incrementing the reference count.

当处理共享对象时,有两种方法来复制一个对象。我们常常将其称为深拷贝和浅拷贝。深拷贝会隐式的
复制一个对象。而钱拷贝只是引用的复制,即只是一个指向共享数据块的指针的复制。做一次深拷贝
会占用很大的内存和CPU资源。然而,做一次浅拷贝则很快,因为那仅仅需要处理指针的设置和引用数目
的增加。


Object assignment (with operator=()) for implicitly shared objects is implemented using shallow copies.

隐式共享对象的赋值是通过浅拷贝来实现的。

The benefit of sharing is that a program does not need to duplicate data unnecessarily, which results in lower memory use and less copying of data. Objects can easily be assigned, sent as function arguments, and returned from functions.

共享的好处是程序不需要对数据进行不必要的复制,这样就降低了内存的使用并且减少了数据的复制。
对象可以容易地被复制,作为函数的参数传递,作为函数的返回值。

Implicit sharing takes place behind the scenes; the programmer does not need to worry about it. Even in multithreaded applications, implicit sharing takes place, as explained in Threads and Implicitly Shared Classes.

隐式共享发生在场景背后,程序员不必担心它。甚至在多线程应用程序中,隐式共享也会像在多线程和隐式共享类中描述
的那样发生。

When implementing your own implicitly shared classes, use the QSharedData and QSharedDataPointer classes.

但要实现你自己的隐式共享类时,可以使用QSharedData和QSharedDataPointer这两个类。

Implicit Sharing in Detail

隐式共享的细节

Implicit sharing automatically detaches the object from a shared block if the object is about to change and the reference count is greater than one. (This is often called copy-on-write or value semantics.)

如果对象即将改变或引用数目大于一时,隐式共享会自动从共享的块上脱离着个对象。(这通常被称为写时拷贝或值语义)

An implicitly shared class has total control of its internal data. In any member functions that modify its data, it automatically detaches before modifying the data.

一个隐式共享类有他内部数据的总控制。在任何成员函数中修改它的数据,它将在数据修改之前,自动脱离共享数据块。

The QPen class, which uses implicit sharing, detaches from the shared data in all member functions that change the internal data.

QPen 类就是一个隐式共享类。在所有修改内部数据的成员函数中,它会脱离共享数据。

Code fragment:

代码片段:

void QPen::setStyle(Qt::PenStyle style)
{
detach();           // detach from common data  从共享数据中脱离
d->style = style;   // set the style member        设置style数据成员
}

void QPen::detach()
{
if (d->ref != 1) {
...             // perform a deep copy  进行一次深拷贝
}
}
List of Classes

类列表

The classes listed below automatically detach from common data if an object is about to be changed. The programmer will not even notice that the objects are shared. Thus you should treat separate instances of them as separate objects. They will always behave as separate objects but with the added benefit of sharing data whenever possible. For this reason, you can pass instances of these classes as arguments to functions by value without concern for the copying overhead.

下面的类列表中,如果他们的对象将要改变时,对象将会从共享数据脱离。程序员甚至没注意到对象是共享数据的。那样你应该
把他们单独的实例当作单独的对象。他们总是表现的像单独的对象一样,但是只要有可能就依然存在添加的数据共享的好处。这
样,你可以通过值将这些类的实例作为参数传递给函数,而不必关心复制的总开销。

Example:

例如:

QPixmap p1, p2;
p1.load("image.bmp");
p2 = p1;                        // p1 and p2 share data 
//p1 和 p2 共享数据。

QPainter paint;
paint.begin(&p2);               // cuts p2 loose from p1 
//p2 自动脱离共享数据。
paint.drawText(0,50, "Hi");
paint.end();
In this example, p1 and p2 share data until QPainter::begin() is called for p2, because painting a pixmap will modify it.

在这个例子中,p1 和 p2 共享数据,直到为p2调用函数QPainter::begin() ,因为画一副图将会改变这幅图。

Warning: Do not copy an implicitly shared container (QMap, QVector, etc.) while you are iterating over it using an non-const STL-style iterator.

警告:当你使用一个非常量STL风格的迭代器在隐式共享容器上进行迭代时,不要复制这个隐式共享的容器(QMap, QVector, 等等)

QBitArray    Array of bits
位数组
QBitmap    Monochrome (1-bit depth) pixmaps
单色的(一位深度)图片
QBrush    Defines the fill pattern of shapes drawn by QPainter
定义用QPainter画出的形状的填充形式
QByteArray    Array of bytes
字节数组
QCache    Template class that provides a cache
提供缓存的模板类
QContiguousCache    Template class that provides a contiguous cache
提供连续的缓存的模板类
QCursor    Mouse cursor with an arbitrary shape
带有任意形状的鼠标
QDir    Access to directory structures and their contents
访问目录的结构和他们的内容
QFileInfo    System-independent file information
系统独立的文件信息
QFont    Specifies a font used for drawing text
指定画文本的字体
QFontInfo    General information about fonts
关于字体的一般信息
QFontMetrics    Font metrics information
字体的韵律信息
QFontMetricsF    Font metrics information
字体的韵律信息
QGLColormap    Used for installing custom colormaps into a QGLWidget
用来向一个QGLWidget安装一个自定义的颜色组
QGradient    Used in combination with QBrush to specify gradient fills
和QBrush结合起来指定填充的渐变风格
QHash    Template class that provides a hash-table-based dictionary
提供一个基于哈希表的目录的模板类
QIcon    Scalable icons in different modes and states
以不同模式和状态伸缩的图标
QImage    Hardware-independent image representation that allows direct access to the pixel data, and can be used as a paint device
硬件独立的图像表示法,允许直接访问像素数据,并且可以用作一个绘画设备。
QKeySequence    Encapsulates a key sequence as used by shortcuts
一个键序列用作快捷键
QLinkedList    Template class that provides linked lists
提供链表的模板类
QList    Template class that provides lists
提供列表的模板类
QLocale    Converts between numbers and their string representations in various languages
在各种各样的语言中转换他们的数字和字符串表示法。
QMap    Template class that provides a skip-list-based dictionary
提供一个基于忽略列表的目录的模板类
QMultiHash    Convenience QHash subclass that provides multi-valued hashes
一个便利的QHash子类提供了多值哈希
QMultiMap    Convenience QMap subclass that provides multi-valued maps
一个便利的QMap子类提供了多值关联
QPainterPath    Container for painting operations, enabling graphical shapes to be constructed and reused
绘画操作的容器,使图画形状可以被构建和被重复利用 
QPalette    Contains color groups for each widget state
包含每个控件状态的颜色组
QPen    Defines how a QPainter should draw lines and outlines of shapes
定义一个a QPainter应该如何画线以及图像的轮廓
QPicture    Paint device that records and replays QPainter commands
绘图设备,可以记录和重演QPainter的命令
QPixmap    Off-screen image representation that can be used as a paint device
屏幕以外的图像表示法可作一个绘图设备
QPolygon    Vector of points using integer precision
整数精确度的点的容器
QPolygonF    Vector of points using floating point precision
浮点数精确度的点的容器
QQueue    Generic container that provides a queue
提供队列的普通容器
QRegExp    Pattern matching using regular expressions
使用正则表达式进行模式匹配
QRegion    Specifies a clip region for a painter
为painer指定一个区域
QSet    Template class that provides a hash-table-based set
提供基于哈希表的集合的模板类
QSqlField    Manipulates the fields in SQL database tables and views
在SQL数据库表和视图中操作领域 
QSqlQuery    Means of executing and manipulating SQL statements
执行和操作SQL语句的方式
QSqlRecord    Encapsulates a database record
浓缩一个数据库记录
QStack    Template class that provides a stack
提供栈的模板类
QString    Unicode character string
Unicode字符编码的字符串
QStringList List of strings
字符串列表
QTextBoundaryFinder    Way of finding Unicode text boundaries in a string
发现一个字符串中Unicode文本边界的方法
QTextCursor    Offers an API to access and modify QTextDocuments
提供一个访问和修改QTextDocuments的应用程序编程接口
QTextDocumentFragment    Represents a piece of formatted text from a QTextDocument
代表从QTextDocument格式化文本的片断
QTextFormat    Formatting information for a QTextDocument
QTextDocument的格式化信息
QUrl    Convenient interface for working with URLs
与URLs一起工作的便利的接口
QVariant    Acts like a union for the most common Qt data types
行为就像一个最普遍的Qt的数据类型的联盟
QVector    Template class that provides a dynamic array
提供动态数组的模板类
QX11Info    Information about the X display configuration

关于X显示配置的信息  

--------------------------------------------------

转载者注:qt上的这个隐式共享技术应该和Linux上的写时复制是一样的吧。

你可能感兴趣的:(Qt)