2011-07-19 36 views
10

Tengo muchos enteros en el rango [0; 2^63-1]. Sin embargo, solo hay enteros de 10^8. Hay sin duplicados. La lista completa se conoce en tiempo de compilación, pero es , solo números aleatorios únicos. Estos números nunca cambian.
Para almacenar un número entero explícitamente, se requieren 8 bytes, y hay valores asociados de 1 byte, por lo que el almacenamiento explícito requiere aproximadamente 860 MB.
Así que quiero encontrar la función hash perfecta mínima para mapear cada uno de 10^8 enteros de [0; 2^63-1] a [0; 10^8-1]. Debería encontrar esta función solo una vez, los datos nunca cambian y la función puede ser complicada. Pero debe ser mínimo, perfecto y el cálculo debe ser rápido. ¿Cómo puedo hacer esto mejor? Tal vez es posible encontrar y utilizar algunas subsecuencias si ocurren?
Gracias.Función hash perfecta mínima

+0

Lista completa conocido en el tiempo de compilación? Entonces, mi consejo sería "asignar" manualmente los números, y luego escribir un script para escupir una declaración estática de un mapa en su lenguaje de programación deseado. Si nunca, nunca cambia, usar una estructura de datos estática para mapear perfectamente los valores sería su solución ideal. Digo 'manualmente' con comillas porque claramente no vas a hacerlo a mano. Vea otros comentarios y respuestas para obtener ideas sobre qué herramientas pueden hacer la asignación para usted. – darvids0n

Respuesta

9

Deje que su ordenador haga el trabajo por usted:

http://www.gnu.org/software/gperf/

Cita: ". Gperf GNU es un generador de funciones hash perfecta Para una lista dada de cuerdas, que produce una función hash y tabla hash, en forma de código C o C++, para buscar un valor dependiendo de la cadena de entrada. La función hash es perfecta, lo que significa que la tabla hash no tiene colisiones, y la búsqueda de tabla hash solo necesita una comparación de cadena. "

+1

pero para esto, [CMPH] (http://cmph.sourceforge.net/) sería mejor ya que fue concebido para crear funciones hash perfectas mínimas para juegos de llaves muy grandes. –

+0

Gracias, probablemente voy a probar ambos. –

3

Estoy trabajando en an algorithm and Java implementation that needs less than 1.6 bits per key.

Anteriormente, he implementado a minimal perfect hash function tool in Java que necesita menos de 2,0 bits por clave.

Otros algoritmos se implementan en CMPH. Por ejemplo, CHD necesita aproximadamente 2,06 bits por tecla de manera predeterminada. Se puede configurar para usar menos espacio, pero la generación es más lenta.

+0

Estoy trabajando en un algoritmo mejorado que necesita menos de 1.58 bits por entrada. –

+0

¿Tiene alguna escritura para su código? Estaba intentando implementarlo para los tipos de datos Largos, pero estaba obteniendo el error de indexoutofbounds – sss999

+0

@ sss999; actualmente no hay mucha documentación; podrías leer los casos de prueba. Tal vez crear un [problema] (https://github.com/thomasmueller/minperf/issues) con un caso de prueba y una excepción, para poder ver cuál podría ser el problema –