Xxhash: Kombinieren von Hashes von Strings

Erstellt am 7. Okt. 2017  ·  6Kommentare  ·  Quelle: Cyan4973/xxHash

Mit 64-Bit-PowerPC möchte ich ein 32-Bit-Hash-Ergebnis über eine Folge von nicht zusammenhängenden Zeichenfolgen.

Gibt es einen Verlust an Hash-Qualität, wenn ich eine Sequenz nicht zusammenhängender Strings mit XXH64 hashe und einfach das Ergebnis jedes Hashs als Seed des nächsten XXH64-Aufrufs übergebe? Außerdem würde ich nur die unteren 32 Bit des Endergebnisses als meinen endgültigen einzelnen 32-Bit-Hash-Wert verwenden, der die Folge von Zeichenfolgen darstellt.

Nachfolgende Hashes, von denen erwartet wird, dass sie gleich sind, werden für die exakt gleiche Sequenz von Zeichenfolgen ausgeführt. Mit anderen Worten, ich brauche nicht, dass der letzte Hash dieser Sequenz "STRING1", "STRING2" mit dem endgültigen Hash von "STRIN", "G1STRING2" identisch ist.

Mein aktueller Code verwendet CRC32 und führt die obigen Schritte aus (Übergabe des Zwischenergebnisses an die nächste Zeichenfolge als Seed)

Vielen Dank.

question

Hilfreichster Kommentar

Egal, ich sehe jetzt, dass XXH64 einen 64-Bit-Seed-Wert zulässt.

Alle 6 Kommentare

Gibt es einen Verlust an Hash-Qualität, wenn ich eine Sequenz nicht zusammenhängender Strings mit XXH64 hashe und einfach das Ergebnis jedes Hashs als Seed des nächsten XXH64-Aufrufs übergebe?

Es gibt einen großen Verlust.

Bitte werfen Sie einen Blick auf die Innenseiten von XXH64_state_t , XXH64_update_endian und XXH64_digest_endian .
Sie können sehen, wie XXH64 die Mitgliedsvariablen von XXH64_state_t verwendet (schreibt und liest). v1 , v2 , v3 , v4 , total_len , um einen Hashwert zu erstellen. Und der Typ dieser Werte ist unsigned long long ( uint_64 , 64-Bit-Ganzzahl ohne Vorzeichen).

Wir können sagen:
(1) Die Gesamtzahl der Bits von XXH64_state ist größer als 64 Bit.
(2) Wenn der Zustand einmal auf einen einzelnen 64-Bit-Wert minimiert (Digest) wird, verschwindet ein großer Teil der Informationen.

Daher können Sie Ihre Annahme nicht erwarten. Bitte denken Sie daran, Streaming-Funktionen zu nutzen.

Wie von @t-mat vorgeschlagen, wurden die Streaming-Funktionen tatsächlich genau für dieses Szenario entwickelt.

Ich nehme an, Sie machen sich Sorgen um die Geschwindigkeit.
Ich glaube nicht, dass Sie etwas gewinnen würden, wenn Sie das Ergebnis von einem Hash zum nächsten weitergeben.
Das Aufrechterhalten eines Streaming-Kontexts ist zwar mit Kosten verbunden, aber auch das Finalisieren eines Hashs. Ich gehe davon aus, dass das Finalisieren des Hashs nach allen paar Bytes tatsächlich mehr kosten würde als die Aufrechterhaltung eines Streaming-Kontexts, bei dem die Finalisierung nur einmal durchgeführt wird, wenn XXH_digest() aufgerufen wird.

Mein Ziel ist es, einen 'Drop-in'-Ersatz für die Verwendung von CRC32 bereitzustellen, um die Geschwindigkeit mit minimalen Codeänderungen an den vielen aufrufenden Sites zu verbessern. Der Streaming-Ansatz ist technisch nicht anwendbar, da der Hash eines in 10-Byte-Blöcke aufgeteilten Streams der gleiche ist wie der Hash desselben Streams, der in 100-Byte-Blöcke unterteilt ist. Die 'Struktur' der nicht zusammenhängenden Strings ist relevant und sollte zum Hash-Ergebnis beitragen.

Dies ist eine Zeichenfolge, die 'indirekte' Verweise auf andere darin eingebettete Zeichenfolgen an beliebigen Stellen (nur eine Ebene tief) enthält. Ich muss die indirekten Strings und die Teilmengen des Basisstrings hashen (ohne die Zeiger auf die indirekten Strings)

Ich habe gesehen, dass die Verwendung von XXH64 auf 64-Bit-Hardware schneller ist und eine bessere Leistung als XXH32 bietet – 32 Bits des Ergebnisses werden als Hash verwendet.

Ich bin mit einer 32-Bit-Hash-Qualität zufrieden, daher schien es vernünftig, den 32-Bit-Hash der verschiedenen Strings als Keim für die Integration des nächsten Strings zu verwenden.

Wenn Ihre vorhandene Programmstruktur dies zulässt, übergeben Sie lieber 64-Bit zwischen 2 aufeinanderfolgenden Hashes. Führen Sie die 32-Bit-Extraktion nur am Ende durch. Es wird die Hash-Qualität maximieren.

Schlagen Sie vor, den Code zu ändern, um einen 64-Bit-Seed zuzulassen? Anstatt einfach die unteren 32 Bits für das Seeding des nächsten Schritts zu extrahieren, xor' ich die hohen 32 und die unteren 32 zusammen, so dass alle 64 Bits zum 32-Bit-Übertrag beitragen. Leider ist es nicht möglich (ohne Daten herumzukopieren), den 64-Bit-Zwischenwert an den nächsten String anzuhängen oder voranzustellen, da ich keine Kontrolle über diesen Speicher habe, er wird mir übergeben.

Egal, ich sehe jetzt, dass XXH64 einen 64-Bit-Seed-Wert zulässt.

War diese Seite hilfreich?
0 / 5 - 0 Bewertungen