5

我有一个QListQVector3D. AQVector3D代表一个顶点或一个点。这个 List 还包含 a 的所有顶点STL-File。问题是一个顶点在列表中存在多次。需要一个 STL 文件的唯一顶点列表。我怎样才能实现它Qt 5.0.2

4

2 回答 2

5

QSet 使用哈希函数来确保值的唯一性(QMap 使用运算符 <) Qt 中没有针对 QVector3D 的 qHash 实现。您可以实现自己的一个,例如:

//place anywhere in Qt-code
#include <QSet>
#include <QVector3D>
#include <QList>

uint qHash(const QVector3D &v)
{
    return qHash( QString( "%1x%2x%3" ).arg(v.x()).arg(v.y()).arg(v.z()) ) ;
}

int foo()
{
    QList<QVector3D> uvector3D_1;
    QSet<QVector3D> uvector3D_2;

    uvector3D_2 = QSet<QVector3D>::fromList(uvector3D_1);
return 0;
}

static int testFoo = foo();

当然它不是最快的,它依赖于 Qt 的函数 qHash 用于 QString。但我认为这对演示很有用。

于 2013-08-13T09:46:28.140 回答
1
QList<QVector3D> originalVector = ...;

然后要么:

QSet<QVector3D> noDublicatesSet = QSet<QVector3D>::fromList(originalVector);

或者

QSet<QVector3D> noDublicatesSet = originalVector.toSet();

如果你需要 QList 回来,你也可以添加类似的东西。

QList<QVector3D> destinationVector = QList<QVector3D>::fromSet(noDublicatesSet);

您还需要这些东西(对不起,它们在我的代码中已经存在很长时间了..忘记了它们是外部的)..您可能想要更改散列函数:

#define ROTL10(x) (((x) << 10) | (((x) >> 22) & 0x000000ff))
#define ROTL20(x) (((x) << 20) | (((x) >> 12) & 0x0000ffff))

uint qHash(double data)
{
union U {
    quint64 n;
    double f;
};
U u;
u.f = data;
return u.f;
}

inline uint qHash(const QVector3D &v, uint seed)
{
return qHash(v.x()) ^ ROTL10(qHash(v.y())) ^ ROTL20(qHash(v.z()));
}

PS 这是 Qt 5.0 的代码,实际上是为向量添加缺少的 qHash(),这就是为什么它们默认不适合 QSet/QHash

于 2013-08-13T08:29:34.717 回答