Vérification de l'arbre binaire de recherche
- L’algorithme de vérification de l’arbre binaire est l’arbre binaire de recherche
- Implémentation de l’algorithme de vérification de l’arbre binaire est l’arbre binaire de recherche
- Analyse de la complexité
Un arbre binaire est une structure de données non linéaire. Il est appelé arbre binaire parce que chaque nœud a un maximum de deux enfants. Ces enfants sont appelés enfants de gauche et enfants de droite. Pour qu’un arbre binaire devienne BST, il doit satisfaire les propriétés suivantes :
- Tous les nœuds du sous-arbre gauche sont plus petits que le nœud racine.
- Tous les nœuds du sous-arbre de droite sont plus grands que le nœud racine.
- Les sous-arbres de gauche et de droite doivent également être des arbres de recherche binaires.
L’algorithme de vérification de l’arbre binaire est l’arbre binaire de recherche
Algorithme 1
Dans cette approche, nous vérifions si le sous-arbre de gauche contient un élément supérieur à la valeur de la racine et si le sous-arbre de droite contient un élément inférieur à la valeur de la racine en considérant chaque nœud comme la racine de son sous-arbre. Pour trouver l’élément max et min, nous devons utiliser deux fonctions distinctes, getMin()
et getMax()
.
getMin()
-
Initialise
temp
en tant queroot
. -
Tant que
temp
a unegauche
, procédez comme suit:- Réglez
temp
surtemp->left
, c’est-à-dire déplacez-vous vers la gauche pour trouver le plus petit élément.
- Réglez
-
Renvoie
temp->val
comme valeur minimale à l’intérieur de ce sous-arbre.
getMax()
-
Initialise
temp
en tant queroot
. -
Tant que
temp
a unright
, procédez comme suit:- Réglez
temp
surtemp->right
, c’est-à-dire déplacez-vous vers la droite pour trouver le plus grand élément.
- Réglez
-
Renvoie
temp->val
comme valeur maximale à l’intérieur de ce sous-arbre.
isBST(root)
-
Si la
root
estNULL
, renvoietrue
. -
Trouvez l’élément maximum
maxm
dans le sous-arbre de gauche en appelantgetMax(root->left)
; -
Trouvez l’élément minimum
minm
dans le sous-arbre de droite en appelantgetMin(root->right)
; -
Si l’élément racine est plus petit que
maxm
ou supérieur àminm
, renvoie false. -
Vérifiez récursivement tous les nœuds en appelant
isBST(root->left)
etisBST(root->right)
. Si les deux appels récursifs retournent true alors l’arbre est BST, retournez true sinon retournez false.
L’algorithme ci-dessus nous dit si un arbre est BST ou non mais est extrêmement lent. Les fonctions getMin()
et getMax()
ont une complexité temporelle de O(n)
dans le pire des cas et sont appelées pour des noeuds n
rendant la complexité temporelle totale O(n2).
Algorithme 2 :
Cet algorithme améliore l’algorithme précédent en n’effectuant pas de calculs répétés. L’approche précédente appelait getMin()
et getMax()
pour chaque noeud. Cette approche améliore l’approche précédente en gardant une trace des valeurs minimales et maximales autorisées lorsque nous traversons les nœuds.
isBST(root)
-
Initialise deux variables
min
commeINT_MIN
etmax
commeINT_MAX
. -
Appelez
isBST(root,min,max)
.
isBST(root, min, max)
-
Si la
root
estNULL
, renvoietrue
. -
Si
min
>root->data
alors la propriété BST est violée, renvoie false. -
Si
max
<root->data
alors la propriété BST est violée, renvoie false. -
Vérifiez récursivement le sous-arbre de gauche en appelant
isBST(root->left, min, root->data-1)
(en passantmin
etroot->data - 1
comme arguments, cela change la plage valide pour BST dans le sous-arbre de gauche) et le sous-arbre de droite en appelantisBST(root->right, root->data+1, max)
(en passantroot->data + 1
etmax
comme arguments, cela change la plage valide pour BST dans le sous-arbre de droite). -
Si les deux appels récursifs renvoient
true
alors l’arbre est BST, retourneztrue
.
La complexité temporelle de cet algorithme est de O(n)
, ce qui est une amélioration significative par rapport à la méthode précédente.
Algorithme 3 :
Cet algorithme évite d’utiliser INT_MIN
et INT_MAX
dans l’algorithme ci-dessus en les remplaçant par deux pointeurs, l
et r
.
isBST(root)
-
Initialise deux nœuds
l
etr
commeNULL
. -
Appelez
isBST(root, l, r)
. (Appel de fonction surchargé)
isBST(root, l, r)
-
Si la
root
estNULL
, renvoietrue
. -
Si
l
n’est pasNULL
etl->data
> =root->data
alors la propriété BST est violée, renvoie false. -
Si
r
n’est pasNULL
etr->data
<=root->data
alors la propriété BST est violée, renvoie false. -
Vérifiez récursivement le sous-arbre de gauche en appelant
isBST(root->left, left, root)
(en passant root comme 3e argument change la limite de valeur minimale pour le sous-arbre) et le sous-arbre de droite en appelantisBST(root->right, root, right)
(passer root comme 2ème argument change la limite de valeur maximale pour le sous-arbre). -
Si les deux appels récursifs renvoient
true
, alors l’arborescence est BST, renvoietrue
.
Algorithme 4 :
Le parcours dans l’ordre de l’arbre binaire de recherche renvoie les éléments dans un ordre trié. Nous pouvons utiliser cette propriété pour vérifier si un arbre binaire est BST. Si tous les éléments de la traversée dans l’ordre ne sont pas en ordre croissant, alors l’arbre donné n’est pas un arbre binaire de recherche.
isBST(root)
-
Initialisez la variable
prev
commeINT_MIN
.prev
est utilisé pour vérifier si le noeud courant est plus grand queprev
et donc suit l’ordre de tri. -
Appelez
isBST(root, prev)
. (Appel de fonction surchargé).
isBST(root,prev)
-
Si la
root
estNULL
, renvoietrue
. -
Vérifier récursivement le sous-arbre gauche par
isBST(root->left, prev)
. S’il renvoiefalse
, alors renvoie false. -
Si
root->data
<=prev
. l’ordre croissant est violé, retourne false. -
Mettre à jour
prev->data
en tant queroot->data
. -
Vérifier récursivement le sous-arbre de droite par
isBST(root->right, prev)
. S’il renvoiefalse
, alors renvoie false. -
Sinon, renvoie vrai.
Implémentation de l’algorithme de vérification de l’arbre binaire est l’arbre binaire de recherche
Algorithme 1
#include <iostream>
using namespace std;
class Node {
public:
int data;
Node *left, *right;
Node(int x) {
this->data = x;
this->left = this->right = NULL;
}
};
int getMin(Node* root) {
while (root->left) {
root = root->left;
}
return root->data;
}
int getMax(Node* root) {
while (root->right) {
root = root->right;
}
return root->data;
}
bool isBST(Node* root) {
if (root == NULL) return true;
if (root->left != NULL && getMax(root->left) > root->data) return false;
if (root->right != NULL && getMin(root->right) < root->data) return false;
if (!isBST(root->left) || !isBST(root->right)) return false;
return true;
}
int main() {
Node* root = new Node(6);
root->left = new Node(3);
root->right = new Node(9);
root->left->left = new Node(1);
root->left->right = new Node(5);
root->right->left = new Node(7);
root->right->right = new Node(11);
if (isBST(root)) {
cout << "This binary tree is a BST." << endl;
} else {
cout << "This binary tree is not a BST." << endl;
}
return 0;
}
Algorithme 2
#include <iostream>
using namespace std;
class Node {
public:
int data;
Node *left, *right;
Node(int x) {
this->data = x;
this->left = this->right = NULL;
}
};
bool isBST(Node* root, int min, int max) {
if (root == NULL) return 1;
if (root->data < min || root->data > max) return 0;
return isBST(root->left, min, root->data - 1) &&
isBST(root->right, root->data + 1, max);
}
bool isBST(Node* root) { return isBST(root, INT_MIN, INT_MAX); }
int main() {
Node* root = new Node(6);
root->left = new Node(3);
root->right = new Node(9);
root->left->left = new Node(1);
root->left->right = new Node(5);
root->right->left = new Node(7);
root->right->right = new Node(11);
if (isBST(root)) {
cout << "This binary tree is a BST." << endl;
} else {
cout << "This binary tree is not a BST." << endl;
}
return 0;
}
Algorithme 3
#include <iostream>
using namespace std;
class Node {
public:
int data;
Node *left, *right;
Node(int x) {
this->data = x;
this->left = this->right = NULL;
}
};
bool isBST(Node* root, Node* l, Node* r) {
if (root == NULL) return true;
if (l != NULL and root->data <= l->data) return false;
if (r != NULL and root->data >= r->data) return false;
return isBST(root->left, l, root) && isBST(root->right, root, r);
}
bool isBST(Node* root) {
Node* l = NULL;
Node* r = NULL;
return isBST(root, l, r);
}
int main() {
Node* root = new Node(6);
root->left = new Node(3);
root->right = new Node(9);
root->left->left = new Node(1);
root->left->right = new Node(5);
root->right->left = new Node(7);
root->right->right = new Node(11);
if (isBST(root)) {
cout << "This binary tree is a BST." << endl;
} else {
cout << "This binary tree is not a BST." << endl;
}
return 0;
}
Algorithme 4
#include <iostream>
using namespace std;
class Node {
public:
int data;
Node *left, *right;
Node(int x) {
this->data = x;
this->left = this->right = NULL;
}
};
bool isBST(Node* root, int& prev) {
if (!root) return true;
if (!isBST(root->left, prev)) return false;
if (root->data <= prev) return false;
prev = root->data;
return isBST(root->right, prev);
}
bool isBST(Node* root) {
int prev = INT_MIN;
return isBST(root, prev);
}
int main() {
Node* root = new Node(6);
root->left = new Node(3);
root->right = new Node(9);
root->left->left = new Node(1);
root->left->right = new Node(5);
root->right->left = new Node(7);
root->right->right = new Node(11);
if (isBST(root)) {
cout << "This binary tree is a BST." << endl;
} else {
cout << "This binary tree is not a BST." << endl;
}
return 0;
}
Analyse de la complexité
Complexité du temps
- Cas moyen
Pour vérifier si l’arbre binaire donné est BST ou non, nous devons traverser tous les noeuds n
car un seul noeud défiant les propriétés conduira à ce que l’arbre ne soit pas BST. La complexité temporelle est donc de l’ordre de [Big Theta] : O(n)
.
- Meilleur cas
Dans le meilleur des cas, la complexité temporelle est de l’ordre de O(n)
. C’est la même chose que la complexité temporelle moyenne.
- Pire cas
La complexité temporelle dans le pire des cas est de l’ordre de O(n)
. Elle est identique à la complexité temporelle du meilleur cas.
Complexité spatiale
La complexité spatiale de l’algorithme est O(n)
en raison de l’espace supplémentaire requis par les appels de récursion.
Harshit Jindal has done his Bachelors in Computer Science Engineering(2021) from DTU. He has always been a problem solver and now turned that into his profession. Currently working at M365 Cloud Security team(Torus) on Cloud Security Services and Datacenter Buildout Automation.
LinkedInArticle connexe - Data Structure
- Arbre binaire de recherche
- Convertir l'arbre binaire en arbre binaire de recherche
- Insertion itérative de l'arbre binaire de recherche
- Successeur de l'arbre de recherche binaire
- Suppression de l'arbre binaire de recherche
- Traversée de l'arbre binaire
Article connexe - Binary Tree
- Arbre binaire de recherche
- Convertir l'arbre binaire en arbre binaire de recherche
- Insertion itérative de l'arbre binaire de recherche
- Successeur de l'arbre de recherche binaire
- Suppression de l'arbre binaire de recherche
- Traversée de l'arbre binaire