/****************tree.h ***********************/
typedef void* (*ProcessItem)(void *, void *);
/**************** BSTNode.c ************************/
typedef struct BinarySearchTreeNode{
void *key;
void *value;
bool visit; // For traversals
struct BinarySearchTreeNode *parent;
struct BinarySearchTreeNode *left;
struct BinarySearchTreeNode *right;
}Node;
typedef struct Tree{ //BST
Node *root;
int size;
}Tree;
static void visitFunc(ProcessItem, Node *);
학습의 일부로서, 다음 (C 코멘트)에 상세한 알고리즘이 대응 코드는 작성된 세 가지 DFS 탐색.
예약 주문 탐색
/*
Pre-order traversal of BST and Binary tree: Node -> Left -> Right
0) Assuming node pointer is pointing to root node, which is, not NULL.
1) Visit node, if not visited
2) From that node,
If left sub-tree exists, and
If root node of that left sub-tree never visted,
then traverse to root node of left sub-tree.
Go to step 1 and continue until a node (that has visted root of left sub-tree) or (that has no left sub-tree exists)
3) From that node,
If right sub-tree exists, and
It root node of right sub-tree not visited,
then traverse to root node of right sub-tree.
Go to step 1 and continue, until a node (that has visited root of right sub-tree) or (that has no right sub-tree exists).
4) We reach this step, because,
Either left/right sub-tree exist but visited
or
left and right sub trees does not exist
Reach parent node and go to step-1 for applying pre-order traversal on that node
*/
static void preOrderTraverse(Node *n, ProcessItem action){
if (n == NULL){
return; // if tree is empty, then go back
}
Node *root = n; // |Step-0
while(root != NULL){
if(root->visit == false){
visitFunc(action, root); // |Step-1: Visit node, if not visited
}
if(root->left != NULL && // |Step-2: if left sub-tree exists, and
(root->left->visit == false)){ // |Step-2: If root node of that left sub-tree's never visted,
root = root->left; // |Step-2: then traverse to root node of left sub-tree.
continue; // |Step-2: Go-to step 1
}
if(root->right != NULL && // |Step-3: if right sub-tree exists,
(root->right->visit == false)){ // |Step-3: If root node of right sub-tree not visited,
root= root->right; // |Step-3: then traverse to root node of right sub-tree.
continue; // |Step-3: Go-to step 1
}
/*
If the instruction pointer points to below insruction, then that means,
Either left/right sub-tree exist but visited
or
left and right sub trees are empty
What can be done now?
Go to parent's tree root node and apply preOrderTraversal
*/
root = root->parent; // |Step-4 Reach parent node.
}
}
후 주문 탐색
/*
Algorithm: Post-order traversal of BST and Binary tree: Left -> Right -> Node
0) Assuming node pointer is pointing to root node, which is, not NULL.
1) From that node,
If left sub-tree exists, and
If root node of that left sub-tree never visted,
then traverse to root node of left sub-tree.
Repeat step 1 until a node (that has visted root of left sub-tree) or (that has no left sub-tree exists)
2) From that node,
If right sub-tree exists, and
If root node of that right sub-tree never visted,
then traverse to root node of right sub-tree.
Go to step 1 and continue until a node (that has visited root of right sub-tree) or (that has no right sub-tree exists)
3) Visit that node, if not visited
4) We reach this step, because,
Either left/right sub-tree exist but all visited
or
left and right sub trees does not exist
Reach parent node and go to step-1 for applying post-order traversal on that node
*/
static void postOrderTraverse(Node *n, ProcessItem action){
if (n == NULL){
return; // if tree is empty, then go back
}
Node *root = n; // |Step-0
while(root !=NULL){
while(root->left != NULL && // |Step-1: If left sub-tree exists, and
(root->left->visit == false)){ // |Step-1: If root node of that left sub-tree never visted,
root=root->left; // |Step-1: then traverse to root node of left sub-tree.
}
if(root->right != NULL && // |Step-2: If right sub-tree exists, and
(root->right->visit == false)){ // |Step-2: If root node of that right sub-tree never visted,
root=root->right; // |Step-2: then traverse to root node of right sub-tree.
continue;
}
visitFunc(action, root); // |Step-3: Visit node, if not visited
/*
If the instruction pointer points to below insruction, then that means,
Either left/right sub-tree exist but all visited
or
left and right sub trees are empty
What can be done now?
Go to parent's tree root node and apply postOrderTraversal
*/
root = root->parent; // |Step-4: Reach parent node.
}
}
에서 주문 통과
,321visitFunc
가
BSTNode.c
에 정의되어 있으며
processItem
사용자로부터 오는 0
,
static void visitFunc(ProcessItem processItem, Node *node){
if(node->visit == TRUE){
return;
}
node->visit=true;
processItem(node->key, node->value);
return;
}
는배경 :
그것은 꽤 분명하다, 즉, 위의 DFS 알고리즘 온라인에서 구할 수 있습니다. 하지만, 내 학습에 따라 이러한 알고리즘에 필요한 세부 수준이 누락되었습니다. 나는 이러한 세부 사항의 부족이 위의 알고리즘에서 다루어 졌다고 생각할 것이다 (C 주석에서). 제 (C 코멘트에서) 언급 한 알고리즘을 강조하고
parent
포인터가 아니라 명시 적 스택을 사용하여 탐색 코드를 대응
내 질문 :
1) 당신은 4 논리적 결함을 볼 수 있나요 3 가지 탐색 모두를위한 단계 알고리즘 및 코드?
2) 위의 코드에서 노드를 방문하기 전에 조건 확인이 필요합니까?
참고 : 탐색 알고리즘의 초급은
'VisitFunc'가 타입이기 때문에 컴파일 타임 오류가 발생합니다. – StoryTeller
예, 유형입니다. 위의 typedef를 볼 수 있습니다. 나는'visitFunc'의 정의를 포함하지 않았습니다. – overexchange
그리고 매개 변수를'action'으로 전달하기 때문에 소문자로 만드는 것은 아무 것도하지 않습니다. 적어도 한 번 컴파일 해 보셨습니까? – StoryTeller