QMap与QHash

关联容器可以保存任意多个具有相同类型的项,且它们由一个键索引。Qt提供两个主要的关联容器类:QMap<K,
T>和QHash<K, T>。

QMap<K,
T>是一个以升序键顺序存储键值对的数据结构。这种排列使它可以提供良好的查找插入性能及键序的迭代。在内部,QMap<K,
T>是作为一个跳越列表(skip-list)来实现执行的。

在映射中插入项的一种简单方式是调用insert():

QMap<QString, int> map;

map.insert("eins", 1);

map.insert("sieben", 7);

map.insert("dreiundzwanzig", 23);

另外,也可以像下面一样,给一个指定的键赋值:

map["eins"] = 1;

map["sieben"] = 7;

map["dreiundzwanzig"] = 23;

[]操作符即可以用于插入也可以用于检索。如果在非常量映射中使用[]为一个不存在的键检索值,则会用给定的键和空值创建一个新的项。为了避免意外的创建空值,可以使用value()函数代替[]操作符来获得项。

int val = map.value("dreiundzwanzig")

如果键不存在,则利用值类型的默认构造函数,将返回一个默认值,同时不会创建新的项。对于基本类型和指针类型,将返回0值。我们可以指定另一默认值作为value()的第二个参数,例如:

int seconds = map.value("delay", 30);

这相当于:

int seconds = 30;

if (map.contains("delay");

seconds =
map.value("delay");

QMap<K,
T>的K和T数据类型可以是与int、double、指针类型、有默认构造函数的类、复制构造函数和赋值操作符相似的基本数据类型。此外,K类型必须提供operator<(),因为QMap<K,
T>要使用这个操作符以提升键序顺序存储项。

QMap<K,
T>的K和T有一对方便的函数keys()和values(),它们在处理小数据集时显的特别有用。它们分别返回映射键的QList和映射值的QList。

映射通常都是单一值的:如果赋予一个现有的键一个新值,则原有的旧值将被该新值取代,以确保两个项不会共有同一个键。通过使用insertMulti()函数或者QMlltiMap<K,
T>方便的子类,可以让多个键值对有相同的键。QMap<K, T>重载了value(const K &),
返回一个给定键多有值的QList列表。例如:

QMultiMap<int, QString> multiMap;

multiMap.insert(1, "one");

multiMap.insert(1, "eins");

multiMap.insert(1, "uno");

QList<QString> vals = multiMap.values(1);

QHash<K,
T>是一个在哈希表中存储键值对的数据结构。它的接口几乎与QMap<K, T>相同,但是与QMap<K,
T>相比,它对K的模板类型有不同的要求,而且它提供了比QMap<K, T>更快的查找功能。

除了对存储在容器类中的所有值类型的一般要求,QHash<K,
T>中K的值类型还需要提供一个operator==(),并需要一个能够为键返回哈希值的全局qHash()函数的支持。Qt已经为qHash()函数提供了对整型、指针型、QChar、QString以及QByteArray。

QHash<K,
T>为它内部的哈希表自动分配最初的存储区域,并在有项被插入或者删除时重新划分所分配的存储区域的大小。也可以通过调用reserve()或者squeeze()来指定或者压缩希望存储到哈希表中的项的数目,以进行性能调整。通常的做法是利用我们预期的最大的项的数目来条用reserve(),然后插入数据,最后如果有多出的项,则调用squeeze()以使内存的使用减到最小。

虽然哈希表通常都是单一值的,但是使用insertMulti()函数或者MultiHash<K,
T>方便的子类,也可以将多个值赋给同一个键。

除了QHash<K,
T>之外,Qt还提供了一个用来高速缓存与键相关联的对象的QCache<K,
T>类以及仅仅存储键的QSet<K>容器。在内部,它们都依赖于QHash<K, T>,且都像QHash<K,
T>一样对K的类型有相同的要求。

最简便的遍历存储在关联容器中多有键值对的方式是使用Java风格的迭代器。因为迭代器必须能同时访问键和值,针对关联容器的Java风格的迭代器与连续容器的在运作方式有些差异。只要区别在于next()和previous()函数返回一个代表键值对的对象,而不是一个简单的值。我们可以使用key()和value()分别从这个对象中获得键和值。例如:

QMap<QString, int> map;

...

int sum = 0;

QMapIterator<QString, int> i(map);

while (i.hasNext())

sum += i.next().value();

如果需要同时存取键和值,可以先忽略next()或previous()的返回值并使用迭代器的key()和value()函数,它们都是针对最后被跳过的项进行操作的:

QMapIterator<QString, int> i(map);

while(i.hasNext()){

i.next();

if (i.value() >
largestValue){

largestKey =
i.key();

largestValue =
i.value();

}

}

===========================================================================================

原文链接:http://newfaction.net/2010/11/17/qt-qhash-and-qmap-difference.html

QMap提供了一个从类项为key的键到类项为T的直的映射,通常所存储的数据类型是一个键对应一个直,并且按照Key的次序存储数据,
这个类也支持一键多值的情况,用类QMultiMap

QHash具有和QMap几乎完全一样的APi,此类维护这一张哈希表,表的大小和数据项是自适应的,QHash是以任意的顺序住址他的数据,,当然了他也是可以支持一键多值的,QMultiHash

两种之间的区别是:
QHash查找速度上显著于QMap
QHash以任意的方式进行存储,而QMap则是以key顺序进行存储
Qhash
的键类型必须提供operator==()和一个全局的qHash(key)函数。而QMap的键类型key必须提供operator<()函数

他们同样也是有两种风格的迭代容器。用来进行遍历的。。
STL 风格的

QMap<key,T>  QMap<key,T>::const_iterator QMap<key,T>::iterator//同样中间那个也是只读的,最后那个是读写的。

下面以一个例子来进行说明:

#include
<QDebug>

int main(int argc, char *argv[])
{
 
  QMap<QString,
QString> map;
   
map.insert("beijing", "111");
 
 
map.insert("shanghai", "021");
 
 
map.insert("tianjin", "022");
 
 
map.insert("chongqing", "023");
 
 
map.insert("jinan", "0531");
 
 
map.insert("wuhan", "027");   

QMap<QString,
QString>::const_iterator i;
 
  for( i=map.constBegin(); i!=map.constEnd(); ++i)
 
     
qDebug() << i.key() <<"
     
 " << i.value();   
 
     
    QMap<QString,
QString>::iterator mi;
 
 
mi = map.find("beijing");
 
  if(mi != map.end())
 
     
mi.value() = "010";
 
  QMap<QString,
QString>::const_iterator modi;
 
 
qDebug() << "";
 
  for( modi=map.constBegin(); modi!=map.constEnd(); ++modi)
 
     
qDebug() << modi.key() <<"
     
 " << modi.value();   
 
  return 0;
}

QMap与QHash,布布扣,bubuko.com

时间: 2024-07-31 14:35:11

QMap与QHash的相关文章

第三十七课、深度解析QMap与QHash

一.QMap深度解析 1.QMap是一个以升序键顺序存储键值对的数据结构 (1)QMap原型为class QMap<K, T>模板 (2).QMap中的键值对根据key进行了排序 (3).QMap中的key类型必须重载operator <     (小于操作符) 2.QMap使用实例一 3.QMap使用实例二 4.QMap的注意事项 (1).通过key获取Value时 A.当key存在,返回对应的Value B.当key不存在,返回值类型所对应的"零"值 (2).插入

第37课 深度解析QMap与QHash

1. QMap深度解析 (1)QMap是一个以升序键顺序存储键值对的数据结构 ①QMap原型为 class QMap<K, T>模板 ②QMap中的键值对根据Key进行了排序 ③QMap中的Key类型必须重载operator< .(即“小于”操作符) (2)QMap使用示例1 QMap<QString, int> map; //注意插入时是无序的 map.insert("key 2", 2); map.insert("key 0", 0

Qt ------- QMap和QHash的区别

基本概念: QMap提供了一个从类项为key的键到类项为T的直的映射,通常所存储的数据类型是一个键对应一个值,并且按照Key的次序存储数据.同时这个类也支持一键多值的情况,用类QMultiMap可以实现. QHash具有和QMap几乎完全一样的APi,此类维护这一张哈希表,表的大小和数据项是自适应的,QHash是以任意的顺序住址他的数据,当然了他也是可以支持一键多值的,用类QMultiHash可以实现. 两者之间的区别是: QHash查找速度上显著于QMap. QHash以任意的方式进行存储,而

QMap 与 QHash

Qt提供的关联容器,QMap.QMultiMap,QHash.QMultiHash和QSet,带有"Multi"字样的容器支持在一个键上面关联多个值. "Hash"容器提供了基于散列函数的更快的查找,而非 Hash 容器则是基于二分搜索的有序集合. 一.QMap.QMultiMap QMap<Key, T>:提供了字典数据结构(关联数组),将类型 T 的值同类型 Key 的键关联起来.通常,每个键与一个值关联.QMap 以键的顺序存储数据:如果顺序无关,

Qt容器类(总结)

Introduction Qt库提供了一组基于模板的一般化的容器类.这些容器可以存储指定的类型的元素.例如,如果你需要一个可变大小的Qstring数组,可以用QVector<QString>.. 这些容器比STL容器更轻更安全更容易使用.如果你不熟悉STL或者更喜欢以Qt的方式做事,你可以用这些类取代STL类. 这些类是隐式共享的,它们都是可重入,它们进行了速度优化,用更少的内存和最小的内联代码扩展,生成更小的可执行文件.此外,当所有的线程仅仅以只读的方式访问它们时,它们是线程安全的. 为了遍

【大话QT之七】QT序列化操作

应用需求: 在网盘开发过程中有这样一个需求.即对文件版本号进行控制,即记录文件版本号的更替信息,这里说的更替信息不过记录不同一时候刻的文件变化,即文件的增.删.改.重命名等操作.在每一个待监控的文件夹下都会保存一份文件.记录文件变化的增量信息.每次低版本号到高版本号升级的时候就能够通过消元合并操作高速地进行.关于文件版本号控制的详细实现方案会在开发完好后列出.这里只指出它的保存方式,即将文件操作的实例对象序列化后保存在文件里. 序列化的实现: 这里我们採用QDataStream来实现序列化,QT

QList内存释放(看它内部存储的是否是Object,另外还有qDeleteAll)

QList<T> 的释放分两种情况: 1.T的类型为非指针,这时候直接调用clear()方法就可以释放了,看如下测试代码 #include <QtCore/QCoreApplication>#include <QList>#include <QString> int main(int argc, char *argv[]){ QCoreApplication a(argc, argv); typedef struct _test { int id; QStr

QtCore Module&#39;s Classes

Qt Core C++ Classes Provides core non-GUI functionality. More... Reference These are links to the API reference materials. C++ Classes Animation Classes Threading Classes Container Classes Plugin Classes Implicitly Shared Classes State Machine Classe

(转)STL

C++容器类 C++中的容器类包括“顺序存储结构”和“关联存储结构”,前者包括vector,list,deque等:后者包括set,map,multiset,multimap等. 若需要存储的元素数在编译器间就可以确定,可以使用数组来存储,否则,就需要用到容器类了. 1.vector 连续存储结构,每个元素是在内存上是连续的: 支持高效的随机访问和在尾端插入/删除操作,但其他位置的插入/删除操作效率低下: 2.deque 连续存储结构,即其每个元素在内存上也是连续的,类似于vector,不同之处