Estructura y algoritmo de datos: algoritmo de árbol transversal de clasificación previa

1. Problema de clasificación multinivel

En el proceso de desarrollo real, a menudo se encontrará el problema de la clasificación de niveles múltiples. Por ejemplo, problemas de clasificación de varios niveles, como la barra de navegación, el menú, la categoría de producto, el enlace de varios niveles, la tabla de diccionario, etc. Luego, puede agregar piddatos relacionados con un campo, que en esencia es en realidad un árbol. El árbol puede resolver muy bien la consulta de la subcategoría de clasificación multinivel.

Inserte la descripción de la imagen aquí

Pero este método tiene un problema fatal: ¡la eficiencia de la consulta es demasiado baja! ! !

Cuando consultamos un nodo hijo en el programa, primero debemos realizar una consulta recursiva desde el nodo raíz. La complejidad del tiempo es O(n).

Entonces, ¿hay alguna manera de mejorar la eficiencia de las consultas del árbol? ¡La respuesta es sí! Se han mejorado muchos árboles en árboles estándar, como árboles binarios, árboles rojo-negro, montones, etc. Pero este no es el punto, lo que quiero compartir hoy es 预排序遍历树算法(MPTT).

MPTTEs precisamente para resolver el problema de la eficiencia de las consultas de los datos relacionales multinivel, es decir, su complejidad temporal puede ser tan eficiente como una constante O(1). ¿No es increíble? Aprendamos juntos el algoritmo del árbol transversal de clasificación previa y veamos cómo se implementa.

Segundo, árbol transversal de clasificación previa

El nombre completo del algoritmo de árbol transversal de clasificación previa es: Modified Preorder Tree Traversalabreviatura MPTT.

1. Mapeo ORM

class Tree(Base, BaseNestedSets):

    __tablename__ = 'tree'

    id = Column(Integer, primary_key=True, autoincrement=True)
    name = Column(String(8), nullable=True, default=None)

    def __repr__(self):
        return f'<Tree(id={self.id}, name={self.name})>'

2. Análisis MPTT

En el código anterior, solo se definen dos campos: id, name. Pero había una base de datos adicional fuera de los 5campos, lfta saber: rgt, level, tree_id, parent_id,.

Estos campos adicionales se utilizan para definir la estructura y jerarquía del árbol. Analicemos cuál es el papel de cada campo.

  • tree_id: Árbol id, utilizado para distinguir cierto árbol entre los muchos árboles de la base de datos.

  • level: Un árbol estándar tendrá altura, profundidad y nivel. El nivel del nodo raíz es 1, y el nivel de los nodos secundarios es el nivel del nodo principal más 1.

  • parent_id: Padre id, el padre iddel nodo, el nodo raíz no tiene padre, por lo que el valor es NULL.

  • lft: El valor de la izquierda del nodo.

  • rgt: El valor correcto del nodo.

El nodo de valores izquierdo y derecho es MPTTel núcleo de este algoritmo, es un lugar particularmente inteligente, la complejidad se reduce al tiempo de recorrido del árbol O(1). A continuación, nos centraremos en analizar cómo los valores izquierdo y derecho atraviesan el árbol.

Una estructura de árbol estándar:

Inserte la descripción de la imagen aquí

Correspondencia de los datos de la base de datos:

Inserte la descripción de la imagen aquí

Jerarquía de datos:

- 【1】
- - 【2】
- - - 【3】
- - 【4】
- - - 【5】
- - - 【6】
- - 【7】
- - - 【8】
- - - - 【9】
- - - 【10】
- - - - 【11】

Atraviesa todo el árbol

Atravesar todo el árbol solo necesita encontrar las tree_idmismas 1condiciones para

Encuentra todos los descendientes de un nodo

Encuentre el nodo a 4todos los descendientes de nodos 4como punto de referencia. El valor es mayor que el de la izquierda 6y el valor de la derecha es menor que 11todos los nodos descendientes, el nodo son 4todos los nodos descendientes.

Encuentra todos los nodos secundarios debajo de un nodo

Encuentre el nodo 1de todos los nodos secundarios 1como punto de referencia. tree_idIgual 1e leveligual 2.

Encuentra la ruta de un nodo

Encuentre el nodo 9todos los caminos más altos 9como punto de referencia. El valor es menor que el izquierdo 14y el derecho es mayor que el valor 15de todos los nodos, el nodo es ``. 9. 的路径。结果是:1 -> 7 -> 8 -> 9 '.

3. Algoritmo de equilibrio MPTT

MPTTAl atravesar rápidamente, pero otras operaciones se volverán muy lentas, por lo que MPTTdebe intentar evitar otras operaciones fuera de la consulta.

Inserte la descripción de la imagen aquí

Entonces, ¿por qué otras operaciones son muy lentas, excepto las operaciones de consulta?

Esto se debe a que la inserción, actualización (movimiento) y eliminación de nodos alterará el equilibrio del árbol. Entonces, al realizar estas operaciones, debe ajustar el número para lograr un nuevo equilibrio.

Agregar

Tomando la operación del nuevo nodo como ejemplo, el algoritmo se puede dividir en los siguientes pasos:

  • Si desea agregar un nuevo nodo a un árbol que no existe, debe crear un nuevo árbol. Entonces no es parent_id, parent_ides NULL, leveles 1, tree_ides el más grande de acuerdo con el árbol tree_idmás existente 1.

  • Si desea agregar un nuevo nodo al árbol existente. Por lo tanto, parent_ides un nodo padre id, levelun nodo padre level, más 1, tree_idy el padre consistente.

  • Repara el valor izquierdo de otros nodos cuyo equilibrio está roto. Es mayor que parent_idlos valores izquierdo y derecho de todos los nodos agregados al valor 2.

  • Repare el valor correcto de otros nodos cuyo equilibrio está roto. Que o igual a parent_idla derecha de todos los nodos del valor correcto más valor 2.

Eliminar

Es similar a aumentar, excepto que después de eliminar un nodo, el valor de la izquierda y el valor de la derecha se invierten, es decir, resta 2.

Actualización (móvil)

Actualizar (mover) es en realidad eliminar un nodo antiguo y agregar uno nuevo. Consulte el ejemplo anterior para conocer el algoritmo específico.

3. Comparación de los pros y los contras de los árboles estándar y los árboles transversales preclasificados

  • 标准树: Adecuado para escenas con muchas adiciones y eliminaciones, y solo es necesario modificar un dato cada vez. En términos de consulta, a medida que aumenta el nivel de clasificación, la eficiencia de la consulta recursiva de la tabla de adyacencia disminuye gradualmente.

  • 预排序遍历树: Aplicable a escenarios con muchas operaciones de consulta. La eficiencia de la consulta no se ve afectada por el aumento del nivel de clasificación. Sin embargo, con el aumento de datos, cada vez que se agregan o eliminan datos, se deben operar varios datos afectados al mismo tiempo, y la eficiencia de ejecución disminuye gradualmente.

No existe un algoritmo perfecto. La estructura de almacenamiento y el algoritmo a elegir en el proceso de desarrollo real deben seleccionarse de acuerdo con el escenario de aplicación específico.

Supongo que te gusta

Origin blog.csdn.net/yilovexing/article/details/107066591
Recomendado
Clasificación