Eines der Dinge, die ich beim Schreiben von Programmen in C vermisse, ist eine Wörterbuchdatenstruktur. Was ist der bequemste Weg, um einen in C zu implementieren? Ich bin nicht auf der Suche nach Leistung, sondern nach einer einfachen Codierung von Grund auf. Ich möchte auch nicht, dass es generisch ist - so etwas wie string-> int reicht aus. Aber ich möchte, dass es eine beliebige Anzahl von Elementen speichern kann.
Dies ist eher als Übung gedacht. Ich weiß, dass es Bibliotheken von Drittanbietern gibt, die man verwenden kann. Aber denken Sie für einen Moment daran, dass sie nicht existieren. In einer solchen Situation können Sie am schnellsten ein Wörterbuch implementieren, das die oben genannten Anforderungen erfüllt.
c
data-structures
dictionary
Rohit
quelle
quelle
Antworten:
Abschnitt 6.6 der Programmiersprache C enthält eine einfache Wörterbuchdatenstruktur (Hashtabelle). Ich denke nicht, dass eine nützliche Wörterbuchimplementierung einfacher sein könnte. Der Einfachheit halber reproduziere ich den Code hier.
Beachten Sie, dass eine Kollision der Hashes zweier Zeichenfolgen zu einer
O(n)
Suchzeit führen kann. Sie können die Wahrscheinlichkeit von Kollisionen verringern, indem Sie den Wert von erhöhenHASHSIZE
. Eine vollständige Beschreibung der Datenstruktur finden Sie im Buch.quelle
hashval = *s + 31 * hashval;
genau 31 und sonst nichts?Der schnellste Weg wäre, eine bereits vorhandene Implementierung wie uthash zu verwenden .
Und wenn Sie es wirklich selbst codieren möchten, können die Algorithmen von
uthash
überprüft und wiederverwendet werden. Es ist BSD-lizenziert, so dass Sie, abgesehen von der Anforderung, den Urheberrechtshinweis zu übermitteln, ziemlich unbegrenzt sind, was Sie damit tun können.quelle
Um die Implementierung zu vereinfachen, ist es schwer, die naive Suche in einem Array zu übertreffen. Abgesehen von einigen Fehlerprüfungen ist dies eine vollständige Implementierung (ungetestet).
quelle
Erstellen Sie eine einfache Hash-Funktion und einige verknüpfte Listen von Strukturen. Weisen Sie je nach Hash zu, in welche verknüpfte Liste der Wert eingefügt werden soll. Verwenden Sie den Hash auch zum Abrufen.
Ich habe vor einiger Zeit eine einfache Implementierung durchgeführt:
quelle
GLib und Gnulib
Dies sind Ihre wahrscheinlich besten Wetten, wenn Sie keine spezifischeren Anforderungen haben, da sie allgemein verfügbar, tragbar und wahrscheinlich effizient sind.
GLib: https://developer.gnome.org/glib/ vom GNOME-Projekt. Mehrere Container sind dokumentiert unter: https://developer.gnome.org/glib/stable/glib-data-types.html, einschließlich "Hash Tables" und "Balanced Binary Trees". Lizenz: LGPL
gnulib: https://www.gnu.org/software/gnulib/ vom GNU-Projekt. Sie sollen die Quelle kopieren und in Ihren Code einfügen. Mehrere Container sind dokumentiert unter: https://www.gnu.org/software/gnulib/MODULES.html#ansic_ext_container, einschließlich "rbtree-list", "linkedhash-list" und "rbtreehash-list". GPL-Lizenz.
Siehe auch: Gibt es Open Source C-Bibliotheken mit gemeinsamen Datenstrukturen?
quelle
Hier ist eine schnelle Implementierung, ich habe es verwendet, um eine 'Matrix' (sruct) aus einem String zu erhalten. Sie können ein größeres Array haben und seine Werte während des Laufs ändern:
quelle
Ich bin überrascht, dass niemand einen Satz von hsearch / hcreate- Bibliotheken erwähnt hat, der zwar nicht unter Windows verfügbar ist, aber von POSIX vorgeschrieben wird und daher in Linux / GNU-Systemen verfügbar ist.
Der Link enthält ein einfaches und vollständiges Basisbeispiel, das seine Verwendung sehr gut erklärt.
Es hat sogar eine thread-sichere Variante, ist einfach zu bedienen und sehr performant.
quelle
Eine Hashtabelle ist die traditionelle Implementierung eines einfachen "Wörterbuchs". Wenn Sie sich nicht für Geschwindigkeit oder Größe interessieren, googeln Sie einfach danach . Es gibt viele frei verfügbare Implementierungen.
Hier ist der erste, den ich gesehen habe - auf einen Blick sieht es für mich in Ordnung aus. (Es ist ziemlich einfach. Wenn Sie wirklich möchten, dass es eine unbegrenzte Datenmenge enthält, müssen Sie eine Logik hinzufügen, um den Tabellenspeicher "neu zuzuweisen", wenn er wächst.)
Viel Glück!
quelle
Hashing ist der Schlüssel. Ich denke, verwenden Sie hierfür die Nachschlagetabelle und den Hashing-Schlüssel. Sie können viele Hashing-Funktionen online finden.
quelle
Die schnellste Methode wäre die Verwendung eines Binärbaums. Sein schlimmster Fall ist auch nur O (logn).
quelle