Ecco un modo per farlo senza appiattire l'albero.
Dalla definizione, qui,
data BinaryTree a = Null | Node (BinaryTree a) a (BinaryTree a)
deriving Show
si può vedere che attraversare l'albero da sinistra a destra, ignorando Node
e le parentesi, ti dà una sequenza alternata di Null
s e a
s. Cioè, tra ogni due valori, c'è un Null
.
Il mio piano è di verificare che ogni sottostruttura soddisfi i requisiti adeguati : possiamo affinare i requisiti in ciascuno di essi Node
, ricordando quali valori ci troviamo tra, quindi testarli in ciascuno di essi Null
. Dato che esiste una Null
coppia di valori tra ogni in ordine, avremo verificato che tutte le coppie in ordine (da sinistra a destra) non sono decrescenti.
Qual è un requisito? È un limite inferiore e superiore allentato sui valori dell'albero. Per esprimere i requisiti, compresi quelli all'estremità più a sinistra e più a destra, possiamo estendere qualsiasi ordine con Bot
tom ed Top
elementi, come segue:
data TopBot a = Bot | Val a | Top deriving (Show, Eq, Ord)
Ora controlliamo che un determinato albero soddisfi i requisiti di essere sia in ordine sia tra determinati limiti.
ordBetween :: Ord a => TopBot a -> TopBot a -> BinaryTree a -> Bool
-- tighten the demanded bounds, left and right of any Node
ordBetween lo hi (Node l x r) = ordBetween lo (Val x) l && ordBetween (Val x) hi r
-- check that the demanded bounds are in order when we reach Null
ordBetween lo hi Null = lo <= hi
Un albero di ricerca binario è un albero che è in ordine e tra Bot
e Top
.
isBSTree :: Ord a => BinaryTree a -> Bool
isBSTree = ordBetween Bot Top
Il calcolo dei valori estremi effettivi in ogni sottostruttura, il loro gorgogliamento verso l'esterno, ti dà più informazioni di quante ne hai bisogno, ed è complicato nei casi limite in cui una sottostruttura sinistra o destra è vuota. Mantenere e verificare i requisiti , spingendoli verso l'interno, è piuttosto più uniforme.
flattenTree
primo. Puoi tornareFalse
presto se un nodo viola la proprietà di ricerca senza dover attraversare l'intera sottostruttura radicata su quel nodo.