QSet in QMap or QHash
我有
例如:
1 2 3 4 5 6 7 8 | QSet<int> intSet; QMap<QSet<int>, char> charSet; intSet.insert(1); intSet.insert(2); intSet.insert(3); charSet.insert(intSet, '6'); |
有什么办法可以使它工作?如果我从
注意:我太在乎性能了
您似乎知道如何使它起作用:定义一个
显然,在无序集合上实现比较器将很困难。我认为,要使其以恒定的时间运行是不可能的。您可以尝试先检查大小,然后再将两个内容排序并比较为列表。
但大致上:不要这样做。这是一种虐待。当然,您可以将集合键的某些内容用于可变数据结构。集合中的整数空间是否固定且较小(即始终在0-1024或其他范围内)?然后尝试存储在QByteArray中的位掩码。等等...
您可以创建这样的哈希方法
1 2 3 4 5 6 7 8 | uint qHash(const QSet<int>& set) { uint seed = 0; for(int x : set) { seed ^= qHash(x) + 0x9e1559a9 + (seed << 6) + (seed >> 2); } return seed; } |
然后您的QMap将像这样
1 | QMap<uint, char> charSet; |
其中uint是先前方法的结果。
实际上这种方式并不是100%稳定的,这取决于您的哈希函数。
似乎您不需要值语义。为何不使用:
1 2 3 | QHash<QSet<int> *, char> charSet; //then to insert a set charSet.insert(& intSet, '6'); |
但是对于每个集合,只有一个字符与一个集合相对应,那么为什么不扩展QSet并添加其他成员呢?
假设您不担心性能(如果您使用容器作为键,我认为这是一个合理的假设),那么我会做这样的事情。
1 2 3 4 5 6 7 8 9 10 | QSet<int> intSet; intSet << 1 << 2 << 3 << 3 << 4; QVector<int> intVector; intVector.reserve(intSet.size()); qCopy(intSet.begin(), intSet.end(), std::back_inserter(intVector)); // QVector doesn't have a std::vector range constructor atm qSort(intVector); QHash<QVector<int>, char> charHash; charHash[intVector] = '6'; |
添加起来会很慢,但是查找应该(相对)快。
我建议您拿出一个更好的钥匙。也许是一个具有固定数量的int的简单类,您只需定义必要的运算符即可使其进入map / hash。