1. 定义:QHash <Key,T> 存储 (键,值) 对,并提供与键相关的值的非常快速的查找。
2. QHash 和 QMap 比较: QHash提供与QMap非常相似的功能。 不同之处是:
- QHash提供比QMap更快的查找。
- 迭代器遍历QMap时 ,项(items)始终按键排序。 使用QHash ,这些项是任意排序的。
- QMap的键类型必须提供运算符 <() 。 QHash的键类型必须提供运算符 ==() 和一个名为 qHash() 的全局哈希函数。
一、示例
#include <QCoreApplication>
#include <QHash>
#include <QHashIterator>
#include <QDebug>
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QHash<QString, int> hash; //定义hash, key:QString, value:int
hash["one"] = 1; //插入数据,方法1: value: <"one",1>
hash.insert("two", 2); //插入数据,方法2: value: <"two",2>
//insert方法进行插入的,每个键只允许一个值
//如果一个键插入多个值,使用QHash::insertMulti(const Key &key, const T &value)
int num1 = hash["one"]; //获取数据,方法1: value: 1
int num2 = hash.value("two"); //获取数据,方法2: value: 2
int time = 30;
if (hash.contains("time")) //查询数据,方法1: value: time = 30
{
time = hash.value("time");
}
int time2 = hash.value("time", 40); //查询数据,方法2: value: time2 = 40
//未查询到,使用第二个参数作为默认值进行返回
hash2.capacity(); //检索大小: value: 10
//**STL样式迭代器遍历**
QHash<QString, int>::const_iterator iter1 = hash.constBegin(); //遍历hash,方法1
while(iter1 != hash.constEnd())
{
qDebug() << iter1.key() << ": " << iter1.value();
++iter1;
}
//**java样式迭代器遍历**
QHashIterator<QString, int> iter(hash); //遍历hash,方法2
while(iter.hasNext())
{
iter.next();
qDebug() << iter.key() << ": " << iter.value();
}
//**检索键的所有值**
QList<int> values = hash.values("one"); //检索key:"one",的所有值
for (int i = 0; i < values.size(); ++i) //对应的插入接口为insertMulti()
{
qDebug() << values.at(i);
}
//**检索某个键**
QHash<QString, int>::iterator iter2 = hash.find("two"); //检索key:"two"
while(iter2 != hash.end() && iter2.key() == "two")
{
qDebug() << iter2.value();
++iter2;
}
//**从hash而不是键中提取值**
foreach (int value, hash)
{
qDebug() << value;
}
return a.exec();
}
二、函数(详细说明)
1. operator[]() :将(键,值)对插入到 hash 中
QHash<QString, int> hash;
hash["one"] = 1; //value: <"one",1>
2. insert() :将(键,值)对插入到 hash 中。
注:QHash 每个键只允许一个值。如果你使用 insert() 插入一个已存在的键,则会删除先前的值。如果想为每个键存储多个值,用 insertMulti()。对应的两套接口为:
- insert() —— value()
- insertMulti() —— values()
QHash<QString, int> hash;
hash.insert("two", 2); //value: <"two",2>
3. operator[]() or value():查找值
QHash<QString, int> hash;
int num1 = hash["one"]; //value: 1
int num2 = hash.value("two"); //value: 2
4. contains():检查哈希是否包含特定键
QHash<QString, int> hash;
int time = 30;
if (hash.contains("time"))
{
time = hash.value("time");
}
5. contains(key, value):检查哈希是否包含特定键,如果没有指定键的项,则使用其第二个参数作为默认值
QHash<QString, int> hash;
int time = 30;
if (hash.contains("time"))
{
time = hash.value("time", 40); //value: time2 = 40
}
注:建议使用 contains() 和 value() 而不是 operator[]() 来查找哈希中的键。原因是使用 operator[]() 时,如果hash中没有这个项存在,默认将项插入到 hash 中,除非 hash 是 const
- contains() & value() 与 operator[]() 查找 hash键 如下:
//错误方式,这将在内存中创建10个item
QHash<int, int> hash2;
for (int i = 0; i < 10; ++i)
{
if (hash2[i] == 1)
{
qDebug() << hash2[i];
}
} //value:<2,0><0,0><1,0>....(10个项)
//正确方式
QHash<int, int> hash3;
for (int i = 0; i < 10; ++i)
{
if (hash3.value(i) == 1)
{
qDebug() << hash3.value(i);
}
} //value:(0个项)
6. capacity():检索 hash 大小
QHash<int, int> hash2;
hash2.capacity();
7. QList<T> values(const Key &key):检索键的所有值,它返回 QList<T>
QHash<QString, int> hash;
QList<int> values = hash.values("one");
for (int i = 0; i < values.size(); ++i)
{
qDebug() << values.at(i);
}
8. find():获取带有键的第一个项的迭代器,并从那里迭代。
QHash<QString, int> hash;
QHash<QString, int>::iterator iter2 = hash.find("two");
while(iter2 != hash.end() && iter2.key() == "two")
{
qDebug() << iter2.value();
++iter2;
}
9. foreach():从哈希(而不是键)中提取值,获取hash中的每个值
QHash<QString, int> hash;
foreach (int value, hash)
{
qDebug() << value;
}
10. remove() 或 QMutableHashIterator::remove():删除任意给定键的项
11. clear():清除整个 hash
12. erase():删除某个键对应的项,与 remove() 和 take() 不同, 该函数不会打乱QHash内部数据结构
三、QHash 遍历
两个方式都可以,可根据习惯使用
1. java样式迭代器遍历
QHash<QString, int> hash;
QHashIterator<QString, int> iter(hash);
while(iter.hasNext())
{
iter.next();
qDebug() << iter.key() << ": " << iter.value();
}
2. STL样式迭代器遍历
QHash<QString, int> hash;
QHash<QString, int>::const_iterator iter1 = hash.constBegin();
while(iter1 != hash.constEnd())
{
qDebug() << iter1.key() << ": " << iter1.value();
++iter1;
}