From c074b18f8d4510713f6d66149213510428eae6f1 Mon Sep 17 00:00:00 2001 From: Christian Kamm <christian.d.kamm@nokia.com> Date: Wed, 7 Sep 2011 08:45:01 +0200 Subject: [PATCH] C++: Improve Literal::hashCode. This can have a dramatic impact on performance when a file contains lots of unique literals. Change-Id: I5309b28f704d7f53e164dc8084ae08354c09354b Reviewed-on: http://codereview.qt.nokia.com/4312 Reviewed-by: Roberto Raggi <roberto.raggi@nokia.com> --- src/libs/3rdparty/cplusplus/Literals.cpp | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/src/libs/3rdparty/cplusplus/Literals.cpp b/src/libs/3rdparty/cplusplus/Literals.cpp index 16eab541d7b..d0aa05d3512 100644 --- a/src/libs/3rdparty/cplusplus/Literals.cpp +++ b/src/libs/3rdparty/cplusplus/Literals.cpp @@ -75,9 +75,21 @@ unsigned Literal::hashCode() const unsigned Literal::hashCode(const char *chars, unsigned size) { - unsigned h = 0; - for (unsigned i = 0; i < size; ++i) - h = (h >> 5) - h + chars[i]; + /* Hash taken from QtCore's qHash for strings, which in turn has the note: + + These functions are based on Peter J. Weinberger's hash function + (from the Dragon Book). The constant 24 in the original function + was replaced with 23 to produce fewer collisions on input such as + "a", "aa", "aaa", "aaaa", ... + */ + + uint h = 0; + + while (size--) { + h = (h << 4) + *chars++; + h ^= (h & 0xf0000000) >> 23; + h &= 0x0fffffff; + } return h; } -- GitLab