No hace mucho, hablé con mi colega y él definitivamente estaba en contra del uso de máscaras de bits porque es difícil entender todos los valores almacenados en la base de datos. En mi opinión, no siempre es una mala idea usarlos, por ejemplo, para determinar los roles del usuario actual. De lo contrario, debe almacenarlo en una tabla separada, lo que provocará una UNIÓN más. ¿Puedes decirme si estoy equivocado? ¿Algún otro efecto secundario, ventajas / desventajas del uso de máscaras de bits?
database
patterns-and-practices
bit
advantages
Alex Ovechkin
fuente
fuente
Respuestas:
Trabajo con una aplicación que usa máscaras de bits para almacenar asignaciones de roles de usuario. Es un dolor en el trasero. Si esto me hace parcial, culpable como acusado.
Si ya está utilizando una base de datos relacional, es un antipatrón que viola la mayoría de la teoría relacional y todas las reglas de normalización. Cuando crea su propio almacenamiento de datos, puede que no sea una mala idea.
Existe la posibilidad de unir demasiadas tablas, pero las bases de datos relacionales están diseñadas para manejar esto. Muchos tienen características adicionales si el rendimiento se convierte en un problema: índices, vistas indexadas, etc. Incluso si los valores que está buscando no cambian con mucha frecuencia, lo cual es una ventaja para Bitmask, lo importante es tener que administrar la indexación. bastante fácil en la base de datos.
Aunque la base de datos hace un buen trabajo al agregar datos, pueden volverse lentos cuando comienza a introducir cosas como fórmulas complejas o funciones escalares en conjuntos de datos. Puede hacer el bit a bit en su aplicación, pero si todo lo que está haciendo es obtener datos relacionados (buscar los roles de un usuario), no está aprovechando lo que su almacenamiento de datos hace mejor.
Mi último argumento en contra sería la simplicidad para otros desarrolladores. Tienes usuarios, roles y tareas. Es un conjunto de relaciones de muchos a muchos (porque hay más de una relación) que es tan común que debería ser fácil de administrar. Es solo cosas CRUDAS.
fuente
where some_bit_mask & 12 > 0
sin un escaneo fila por fila.user_role_map
ouser_priv_map
mesa habría sido suficiente.Ya ha nombrado los pros y los contras relevantes:
Decidir qué hacer requiere más información:
Entonces, lo que tiene que hacer es reunir los factores de riesgo y luego ponderarlos , para ver si los profesionales superan a los contras.
fuente
Si está realmente, realmente , realmente limitado para el espacio en disco, entonces podría considerar mapas de bits para permisos de usuario. Si el rendimiento es tu preocupación, entonces olvídate de ellos por completo, porque separarlos en realidad será más lento. No puede indexar un campo de mapa de bits de manera significativa, lo que resulta en escaneos de la tabla de la base de datos, que [casi] siempre son un factor decisivo para el rendimiento.
A menos que sea Amazon o Netflix, la cantidad de datos involucrados en los permisos de los usuarios será insignificante en comparación con todo lo demás que tiene.
Cualquier DBMS serio puede manejar esa "unión extra" sin siquiera parpadear.
fuente
Cuando el almacenamiento era costoso, la bendición con las máscaras de bits era que ahorraban espacio. En los días de Big Data, este no es el problema que alguna vez fue.
Tomando el ejemplo que usted cita: tener roles almacenados como una máscara de bits sería una especie de olor a código desde el punto de vista del diseño de la base de datos, ya que violaría la primera forma normal . En este sentido, son un antipatrón.
Dicho todo esto, no tiene que ser uno ni el otro. Puede almacenar los datos como una máscara de bits y luego tener una vista que pueda extraer los roles de los usuarios sobre la marcha. También tendría la ventaja de comprobar de un vistazo qué usuarios tenían los mismos roles.
fuente
La única ventaja de usar máscaras de bits es si el significado de los campos de bits no es estático. Las tablas relacionales solo funcionan bien si sabe de antemano qué es cada campo en un registro:
CREATE TABLE
después de todo, debe identificar los campos en la declaración DDL.Si el significado de cada campo de bit es configurable en tiempo de ejecución, o si no se conoce de antemano, entonces podría tener sentido almacenar booleanos como un campo de bit. Incluso entonces, es posible definir una tabla con los campos arbitrarios:
field_1
,field_2
, etc. Esto le da un diseño relacional más limpio, aunque todavía no es ideal. Si esto es preferencial a un campo de bits es en gran medida una cuestión de opinión, ya que ninguna de las soluciones es ideal.Si sabe lo que representan los bits durante el desarrollo, cree campos para cada bit y asígneles nombres significativos .
Solo tenga cuidado con el efecto de plataforma interna . Si terminas definiendo campos arbitrarios pero bien escritos, eso es una cosa, pero si vas mucho más allá de eso, reinventarás una base de datos relacional ... dentro de una base de datos relacional.
fuente
Soy ambivalente sobre las máscaras de bits. Me parece que la mayoría de sus detractores no entienden binario y hexadecimal. Para mayor claridad, usa buenos mnemónicos.
Una ventaja no mencionada anteriormente es la capacidad de agregar un nuevo significado a las máscaras de bits sin la adición de una nueva columna que puede llevar mucho tiempo. Nuestros diseñadores de db (que me precedieron) los tienen en una tabla que ahora obtiene 5 millones de nuevos registros diarios. Agregar una nueva columna para representar un nuevo comportamiento llevaría mucho tiempo, mientras que definir un nuevo bit (hemos consumido 33 de 64) no requiere la reconstrucción de la tabla.
No, las máscaras de bits no se pueden indexar, pero crear 33 índices sería ridículo y ralentizaría las inserciones en un rastreo. Las búsquedas de tablas utilizan los índices de "propietarios" de fechas y registros, por lo tanto, los índices en esta máscara de bits, si es posible, nunca se utilizarían.
fuente
Si el objetivo es solo ahorrar algo de espacio en disco, creo que es una mala idea:
Sin embargo, hay algunos casos que pueden justificar el uso de campos de bits:
fuente