C ++ Standard Template Library (STL) are defined in a series of containers, and the container should have a number of classes and operations iterator container used (this part can be found in my blog , "the study notes --STL C ++ Standard Template Library" ). Custom Qt several containers, these containers are also based on a template can be instantiated as a specific data type. Compared to the STL container, container in the Qt more compact, safe and easy to use, but for speed and memory optimization, in addition, they are also thread-safe, as the container is a read-only access by multiple threads.
STL and similar containers into the order containers Qt and the associated container. The former is a linear table data structure, which data structure is a tree. Sequential container class has QList, QLinkedList, QVector, QStack, QQueue; associated containers comprising QMap, QMultiMap, QHash, QMultiHash, Qset. Also the use of iterative data item classes to access the container, Qt provides Java classes and types of iterations of the iterative type STL class. Java type of iteration is easy to apply and provides advanced functionality, and iterative efficiency of the STL types will be higher.
container
QList
Qlist container is the most common type, which stores a set of data of type T is. Its core is achieved by way of storage array list, which makes the acquisition by way of a subscript value very quickly. Qlist to be common CRUD interfaces:
interface |
description |
insert() |
Insert data |
removeAt() |
Delete certain data |
removeFirst() |
Remove header |
removeLast() |
Delete End |
repalce() |
Change Data |
move() |
Mobile Data |
swap() |
Data exchange |
append |
Increasing the data in front of the head |
prepend |
After the end of data increases |
at() |
A fast access location data, similar to the index data |
isEmpty() |
Determining whether the container is empty |
size() |
Analyzing the data size of the container |
QList<int> integerList;
QList<QDate> dateList;
QLinkedList
QLinkedList linked list, like a QList, but the data item is not stored in a continuous memory, which is based on the iterative access a data item, and inserted into the same operating time and delete data items. Except that provides access to data items based subscripted, the other interface function with QList QLinkedList substantially the same.
QLinkedList<int> integerList;
QLinkedList<QTime> timeList;
QVector
Qvector provide dynamic array of functions, the standard index to access the data. QList QVector and function interface nearly identical, but because QVector items are stored contiguously, the data inserted in its first intermediate position or efficiency may be very slow.
QVector<int> integerVector;
QVector<QString> stringVector;
QStack
QStack after similar LIFO stack, first-out type container. The basic interface is a push () and pop ().
QStack<int> stack;
stack.push(1);
stack.push(2);
stack.push(3);
while (!stack.isEmpty())
cout << stack.pop() << endl;
QQueue
Queue is similar to the first in first out queue FIFO containers. It's basic interface is enqueue () and dequeue ().
QQueue<int> queue;
queue.enqueue(1);
queue.enqueue(2);
queue.enqueue(3);
while (!queue.isEmpty())
cout << queue.dequeue() << endl;
QSet
QSet is a collection of individual data. Based on the hash table, the data stored in the order is uncertain. Find value very quickly.
QSet<QString> set;
set.insert("one");
set.insert("three");
set.insert("seven");
if (!set.contains("ninety-nine"))
QMap
QMap <Key, T> provides an associative array, a key (key) is mapped to a (key). QMap stores data in the order of the keys, i.e. it will automatically sort. If we do not sort, QHash would be better used.
QMap<QString, int> map;
map["one"] = 1;
map["three"] = 3;
map["seven"] = 7;
map.insert("twelve", 12);
int num1 = map["thirteen"];
int num2 = map.value("thirteen");
QMultiMap
QMultiMap <Key, T> T is a subclass QMap for processing multi-value map (a key corresponding to a plurality of values). Note that, QMultiMap not available [] operator can only obtain the value and the value of values, the return value is QList <T>.
QMultiMap<QString, int> map1, map2, map3;
map1.insert("plenty", 100);
map1.insert("plenty", 2000);
// map1.size() == 2
map2.insert("plenty", 5000);
// map2.size() == 1
map3 = map1 + map2;
// map3.size() == 3
QList<int> values = map.values("plenty");
for (int i = 0; i < values.size(); ++i)
cout << values.at(i) << endl;
QHash
QHash <Key, T> dictionary function is achieved based on the hash table template class, function and usage and QMap basically the same, but QHash find faster data items are not sorted automatically.
QHash<QString, int> hash;
hash["one"] = 1;
hash["three"] = 3;
hash["seven"] = 7;
hash.insert("twelve", 12);
int num1 = hash["thirteen"];
int num2 = hash.value("thirteen");
QMultiHash
QMultiHash is a subclass QHash for processing multifunctions. Its usage and QHash similar. Similarly, QMultiHash not available [] operator can only obtain the value and the value of values, the return value is QList <T>.
QMultiHash<QString, int> hash1, hash2, hash3;
hash1.insert("plenty", 100);
hash1.insert("plenty", 2000);
// hash1.size() == 2
hash2.insert("plenty", 5000);
// hash2.size() == 1
hash3 = hash1 + hash2;
// hash3.size() == 3
QList<int> values = hash.values("plenty");
for (int i = 0; i < values.size(); ++i)
cout << values.at(i) << endl;
Iterator
Java iterator type
For each container type Java class has two iterators, one for the read-only operations, one for read and write operations.
Containers |
Read-only iterator |
Read-write iterator |
QList<T>, QQueue<T> |
QListIterator<T> |
QMutableListIterator<T> |
QLinkedList<T> |
QLinkedListIterator<T> |
QMutableLinkedListIterator<T> |
QVector<T>, QStack<T> |
QVectorIterator<T> |
QMutableVectorIterator<T> |
QSet<T> |
QSetIterator<T> |
QMutableSetIterator<T> |
QMap<Key, T>, QMultiMap<Key, T> |
QMapIterator<Key, T> |
QMutableMapIterator<Key, T> |
QHash<Key, T>, QMultiHash<Key, T> |
QHashIterator<Key, T> |
QMutableHashIterator<Key, T> |
For sequential containers QList like, the pointer is not Java type iterator points to a data item, but between data items.
QList<QString> list;
list << "A" << "B" << "C" << "D";
QListIterator<QString> i(list);
while (i.hasNext())
qDebug() << i.next();
For the above read-only traverse the container as a constructor parameter list passed to the iterator i, the pointer is pointing to the front of the iteration (in front of A) a data item in the first list, call hasNext () function to later determines whether the iterator there are data items. If so, skip the next call to a data item, and returns the next hop that data items of the past. You can reverse traversal:
QListIterator<QString> i(list);
i.toBack();
while (i.hasPrevious())
qDebug() << i.previous();
Common iterator interface pointer movement and reading of data are:
Function |
Behavior |
toFront () |
Moves the iterator to the front of the list (before the first item) |
toBack() |
Moves the iterator to the back of the list (after the last item) |
hasNext() |
Returns true if the iterator isn't at the back of the list |
next() |
Returns the next item and advances the iterator by one position |
peekNext() |
Returns the next item without moving the iterator |
hasPrevious() |
Returns true if the iterator isn't at the front of the list |
previous() |
Returns the previous item and moves the iterator back by one position |
peekPrevious() |
Returns the previous item without moving the iterator |
上述为只读迭代器,若要对数据进行修改,则需要使用QMutableListIterator。如:
QMutableListIterator<int> i(list);
while (i.hasNext())
{
if (i.next() > 128)
i.setValue(128);
}
对于关联容器QMap<key T>,使用QMapIterator和QMutableMapIterator迭代器类。他们具有上表中所有的接口,并增加了key()和value()函数用以获取刚刚跳过的数据项的键和值。如果在多值容器中遍历,可以用findNext或findPrevious函数查找下一个或上一个值。
QMap<int, QWidget *> map;
QHash<int, QWidget *> hash;
QMapIterator<int, QWidget *> i(map);
while (i.hasNext())
{
i.next();
hash.insert(i.key(), i.value());
}
//if there are multi values
QMutableMapIterator<int, QWidget *> i(map);
while (i.findNext(widget))
i.remove();
STL类型迭代器
STL迭代器与Qt和STL兼容,并且进行了速度优化。对于每个容器类都有两个STL类型迭代器,一个用于只读操作,另一个用于读写操作。若无须修改数据时一定要使用只读迭代器,因为它们速度更快。
Containers |
Read-only iterator |
Read-write iterator |
QList<T>, QQueue<T> |
QList<T>::const_iterator |
QList<T>::iterator |
QLinkedList<T> |
QLinkedList<T>::const_iterator |
QLinkedList<T>::iterator |
QVector<T>, QStack<T> |
QVector<T>::const_iterator |
QVector<T>::iterator |
QSet<T> |
QSet<T>::const_iterator |
QSet<T>::iterator |
QMap<Key, T>, QMultiMap<Key, T> |
QMap<Key, T>::const_iterator |
QMap<Key, T>::iterator |
QHash<Key, T>, QMultiHash<Key, T> |
QHash<Key, T>::const_iterator |
QHash<Key, T>::iterator |
STL类型迭代器是数组的指针,所以可以只用++ -- += -=运算符移动位置用解除引用运算符*获取其值。与JAVA类型迭代器不同,STL类型迭代器直接指向数据项。
begin()函数使迭代器指向容器的第一个数据项,end()函数使函数指向一个虚拟的标识结尾的数据项。end()表示的数据项是无效的,一般用作循环结束的判断条件。
对于QList等顺序容器,其通常用法为:
QList<QString>::const_iterator i;
for (i = list.constBegin(); i != list.constEnd(); ++i)
qDebug() << *i;
对于QMap等关联容器类,其通常用法为:
QMap<int, int> map;
...
QMap<int, int>::const_iterator i;
for (i = map.constBegin(); i != map.constEnd(); ++i)
qDebug() << i.key() << ':' << i.value();
foreach关键字
这里还要提到上篇笔记QtGlobal头文件中定义了一个foreach关键字,其作用为遍历容器中所有的项。语法为:
foreach (variable, container)
statement.
可以看到使用foreach比使用迭代器更加简洁,像是一个for循环,对于多值映射可以用两层foreach来实现。
QLinkedList<QString> list;
...
foreach (const QString &str, list)
qDebug() << str;
QMap<QString, int> map;
...
foreach (const QString &str, map.keys())
qDebug() << str << ':' << map.value(str);
QMultiMap<QString, int> map;
...
foreach (const QString &str, map.uniqueKeys())
{
foreach (int i, map.values(str))
qDebug() << str << ':' << i;
}