Je cherchais une implémentation efficace de String trie. Surtout, j'ai trouvé du code comme celui-ci:
Implémentation référentielle en Java (par wikipedia)
Je n'aime pas ces implémentations pour principalement deux raisons:
- Ils ne prennent en charge que 256 caractères ASCII. Je dois couvrir des choses comme cyrillique.
- Ils sont extrêmement inefficaces en mémoire.
Chaque nœud contient un tableau de 256 références, soit 4096 octets sur une machine 64 bits en Java. Chacun de ces nœuds peut avoir jusqu'à 256 sous-nœuds avec chacun 4096 octets de références. Ainsi, un Trie complet pour chaque chaîne de caractères ASCII 2 nécessiterait un peu plus de 1 Mo. Trois chaînes de caractères? 256 Mo uniquement pour les tableaux dans les nœuds. Etc.
Bien sûr, je n'ai pas l'intention d'avoir les 16 millions de chaînes de caractères en trois dans mon Trie, donc beaucoup d'espace est juste gaspillé. La plupart de ces tableaux ne sont que des références nulles car leur capacité dépasse de loin le nombre réel de clés insérées. Et si j'ajoute unicode, les tableaux deviennent encore plus grands (char a 64k valeurs au lieu de 256 en Java).
Y a-t-il un espoir de faire un tri efficace pour les cordes? J'ai envisagé quelques améliorations par rapport à ces types d'implémentations:
- Au lieu d'utiliser un tableau de références, je pourrais utiliser un tableau de type entier primitif, qui indexe dans un tableau de références à des nœuds dont la taille est proche du nombre de nœuds réels.
- Je pourrais briser les chaînes en parties de 4 bits qui permettraient des tableaux de nœuds de taille 16 au prix d'un arbre plus profond.
si vous encodez les chaînes en UTF8, vous pouvez utiliser le tri de branchement 256 standard et toujours être compatible unicode
vous devez également noter que seuls 70 caractères environ sur les 128 caractères ascii possibles (qui codent tous en 1 octet en UTF8) seront trouvés le plus lourdement que vous pouvez optimiser pour cela (comme inclure les digraphes communs à la place des caractères de contrôle inutilisés )
la source
byte*
pour encoder n'importe quel type dans un tri au niveau du bit.