#include <stdio.h>
#include <stdlib.h>
#pragma warning (disable : 4996)
typedef struct tree
{
int value;
struct tree* left;
struct tree* right;
}tree;
tree* insertNodeTree(tree* t, int data);
tree* getMaxNode(tree* t);
tree* getMinNode(tree* t);
tree* getSearchNode(tree* t, int target);
void displayBST(tree* t);
void memoryFree(tree* t);
int getSumTreeNode(tree* t);
int getCountTreeNode(tree* t);
tree* removeNodeTree(tree* t, int target);
tree* insertNodeTree(tree* t, int data)
{
if(t == NULL)
{
t = (tree*)malloc(sizeof(tree));
t->value = data;
t->left = NULL;
t->right = NULL;
}
else if(t->value < data)
{
t->right = insertNodeTree(t->right, data);
}
else if(t->value > data)
{
t->left = insertNodeTree(t->left, data);
}
return t;
}
tree* getMaxNode(tree* t)
{
if (t != NULL)
{
while(t->right != NULL)
t = t->right;
}
return t;
}
tree* getMinNode(tree* t)
{
if (t != NULL)
{
while(t->left != NULL)
t = t->left;
}
return t;
}
tree* getSearchNode(tree* t, int target)
{
if (t != NULL)
{
if(t->value == target)
return t;
else if(t->value < target)
return getSearchNode(t->right, target);
else
return getSearchNode(t->left, target);
}
return t;
}
void displayBST(tree* t)
{
if(t != NULL)
{
displayBST(t->left);
printf("%d ", t->value);
displayBST(t->right);
}
}
void memoryFree(tree* t)
{
if(t != NULL)
{
memoryFree(t->left);
memoryFree(t->right);
printf("%d 메모리 제거\n", t->value);
free(t);
}
}
int getSumTreeNode(tree* t)
{
if(t != NULL)
return getSumTreeNode(t->left) + getSumTreeNode(t->right) + t->value;
return 0;
}
int getCountTreeNode(tree* t)
{
if(t != NULL)
return getCountTreeNode(t->left) + getCountTreeNode(t->right) + 1;
return 0;
}
tree* removeNodeTree(tree* t, int target)
{
tree* temp;
if (t != NULL)
{
if(t->value == target)
{
if(t->left == NULL && t->right == NULL)
{
free(t);
printf("\n\n\t\t/case 1. 삭제할 노드의 자식 노드가 없는 경우\n");
return NULL;
}
else if(t->right == NULL)
{
temp = t->left;
free(t);
printf("\n\n\t\tcase 2. 왼쪽 자식 노드만 있는 경우\n");
return temp;
}
else if(t->left == NULL)
{
temp = t->right;
free(t);
printf("\n\n\t\tcase 3. 오른쪽 자식 노드만 있는 경우\n");
return temp;
}
else
{
temp = getMaxNode(t->left);
t->value = temp->value;
printf("\n\n\t\tcase 4. 자식 노드가 둘 다 있는 경우 => 삭제되는 것이 아니라 왼쪽 자식 중 최댓값을 대입\n");
printf("\t\t왼쪽 자식 중 최댓값을 제거하러 다시 출발!(재귀호출)\n");
t->left = removeNodeTree(t->left, temp->value);
}
}
else if(t->value < target)
{
t->right = removeNodeTree(t->right, target);
}
else
{
t->left = removeNodeTree(t->left, target);
}
}
return t;
}
int main()
{
tree* findNode = NULL;
tree* root = NULL;
int data;
while (1)
{
system("cls");
printf("\n\n\t * Binary Search Tree, BST *\n");
printf("1. 원소 삽입\n");
printf("2. 원소 삭제\n");
printf("3. 원소 검색\n");
printf("4. 최댓값 구하기\n");
printf("5. 최솟값 구하기\n");
printf("6. 이진 검색 트리 출력\n");
printf("7. 트리 노드의 합\n");
printf("8. 트리 노드의 개수\n");
printf("0. 프로그램 종료\n");
printf("\n메뉴 선택: ");
int choice;
scanf("%d", &choice);
switch (choice)
{
case 1:
printf("\n\n삽입할 노드의 값 입력: ");
scanf("%d", &data);
root = insertNodeTree(root, data);
break;
case 2:
printf("\n\n제가할 노드의 값을 입력: ");
scanf("%d", &data);
root = removeNodeTree(root, data);
break;
case 3:
printf("\n\n검색 노드의 값을 입력: ");
scanf("%d", &data);
findNode = getSearchNode(root, data);
if(findNode == NULL)
printf("\n\n\t\t검색 노드는 존재하지 않습니다.\n");
else
printf("\n\n\t\t검색한 노드는 %p번지에 저장되어 있습니다.\n", findNode);
break;
case 4:
findNode = getMaxNode(root);
if(findNode == NULL)
printf("\n\n\t\t최댓값 노드를 찾을 수 없습니다.\n");
else
printf("\n\n\t\t최댓값 노드는 %d입니다.\n", findNode->value);
break;
case 5:
findNode = getMinNode(root);
if(findNode == NULL)
printf("\n\n\t\t최솟값 노드를 찾을 수 없습니다.\n");
else
printf("\n\n\t\t최솟값 노드는 %d입니다.\n", findNode->value);
break;
case 6:
printf("\n\nBST Display: ");
displayBST(root);
break;
case 7:
printf("\n\n\t\tBST 노드의 합은 %d입니다.\n", getSumTreeNode(root));
break;
case 8:
printf("\n\n\t\tBST 노드의 개수는 %d입니다.\n", getCountTreeNode(root));
break;
case 0:
memoryFree(root);
return 0;
}
printf("\n\n\t\t");
system("pause");
}
return 0;
}