二叉搜索樹(BST)

二叉搜索樹(Binary Searching Tree)
記住的特點就是左邊的key<=根的key 右邊的key>=根的key
定義:支持多種動態集合操作,插入、刪除、找最小值、最大值、前驅、後繼、查找。
用途:即可做字典,也可以做優先隊列。
時間複雜度:基本操作時間和樹的高度成正比。對於n個節點的完全二叉樹,最壞運行時間O(lgn).如果樹是含n個節點 線性鏈,則最壞操作時間是o(n)。平均時間O(lgn)。

STL中的map容器就是使用的這個。

數據結構

struct node
{
int _id;
char _value;
struct node* l_node;
struct node* r_node;
};

插入結點

#include <stdio.h>
#include <stdlib.h>
typedef struct _Node
{
	unsigned _key;
	char _value;
	struct _Node * _left;
	struct _Node * _right;
} Node, *PNode;


PNode make_node(unsigned key, char value);
PNode insert_node(PNode root, PNode node);
PNode header = NULL;
int main(int ac, char * av[])
{
	PNode root = NULL;
	PNode node = make_node(5, 'a');
	root = insert_node(root, node);
    node = make_node(3, 'b');
	root = insert_node(root, node);
    node = make_node(6, 'c');
	root = insert_node(root, node);

	return 0;
}
PNode make_node(unsigned key, char value)
{
	PNode node = (PNode)(malloc(sizeof(Node)));
	if (node)
	{
		node->_key = key;
		node->_value = value;
		node->_left = NULL;
		node->_right = NULL;
	}
	return node;
}
PNode insert_node(PNode root, PNode node)
{
	if (!root)
	{
		return node;
	}
	if (root->_key == node->_key)
	{
		root->_value = node->_value;
	}
	else if (root->_key > node->_key)
	{
		root->_left = insert_node(root->_left, node);
	}
	else
	{
		root->_right = insert_node(root->_right, node);
	}
	return root;
}

刪除結點

分四種情況討論:

  1. 要刪除的結點是葉子結點,則直接刪除
  2. 要刪除的結點是中間某個結點,有右子節點
  3. 有左子節點,與2情況想同,但是代碼不同
  4. 有左右子節點,找左側最大或者右側最小的替換他,是他變成葉子結點,然後刪掉。
#include <stdio.h>
#include <stdlib.h>
typedef struct _Node
{
	unsigned _key;
	char _value;
	struct _Node * _left;
	struct _Node * _right;
} Node, *PNode;



PNode make_node(unsigned key, char value);
PNode insert_node(PNode root, PNode node);
PNode find_max(PNode root);
void exchange(PNode node1, PNode node2);
PNode process_remove(PNode root, bool * is_exchange);
PNode remove_node(PNode root, unsigned key);

PNode header = NULL;
int main(int ac, char * av[])
{
	PNode root = NULL;
	PNode node = make_node(5, 'a');
	root = insert_node(root, node);
	node = make_node(3, 'b');
	root = insert_node(root, node);
	node = make_node(6, 'c');
	root = insert_node(root, node);
	root = remove_node(root, 6u);

	return 0;
}
PNode make_node(unsigned key, char value)
{
	PNode node = (PNode)(malloc(sizeof(Node)));
	if (node)
	{
		node->_key = key;
		node->_value = value;
		node->_left = NULL;
		node->_right = NULL;
	}
	return node;
}
PNode insert_node(PNode root, PNode node)
{
	if (!root)
	{
		return node;
	}
	if (root->_key == node->_key)
	{
		root->_value = node->_value;
	}
	else if (root->_key > node->_key)
	{
		root->_left = insert_node(root->_left, node);
	}
	else
	{
		root->_right = insert_node(root->_right, node);
	}
	return root;
}
PNode find_max(PNode root)
{
	PNode temp = root;
	while (temp->_right)
	{
		temp = temp->_right;
	}
	return temp;
}
void exchange(PNode node1, PNode node2)
{
	unsigned key = node1->_key;
	char value = node1->_value;
	node1->_key = node2->_key;
	node1->_value = node2->_value;
	node2->_key = key;
	node2->_value = value;
}
PNode process_remove(PNode root, bool * is_exchange)
{
	bool has_left = root->_left, has_right = root->_right;
	PNode node = NULL;
	if (!has_left && !has_right)
	{
		free(root);
		node = NULL;
	}
	else if (has_left && !has_right || has_right && !has_left)
	{
		if (has_left && !has_right)
		{
			node = root->_left;
			free(root);
			root = NULL;
		}
		else
		{
			node = root->_right;
			free(root);
			root = NULL;
		}
	}
	else
	{
		PNode max_node = find_max(root->_left);
		exchange(max_node, root);
		*is_exchange = true;
	}
	*is_exchange = false;
	return node;
}
PNode remove_node(PNode root, unsigned key)
{
	bool is_exchanged = false;
	if (root == NULL)
	{
		return NULL;
	}
	if (root->_key == key)
	{
		root = process_remove(root, &is_exchanged);
		/*如果沒交換*/
		if (!is_exchanged)
		{
			return root;
		}
	}
	if (root->_key > key || is_exchanged)
	{
		root->_left = remove_node(root->_left, key);
	}
	else if (root->_key < key)
	{
		root->_right = remove_node(root->_right, key);
	}
	return root;
}

深度優先遍歷

#include <stdio.h>
#include <stdlib.h>
typedef struct _Node
{
	unsigned _key;
	char _value;
	struct _Node * _left;
	struct _Node * _right;
} Node, *PNode;



PNode make_node(unsigned key, char value);
PNode insert_node(PNode root, PNode node);
void visit_node(PNode node);
void pre_order(PNode root);
void post_order(PNode root);
void in_order(PNode root);
PNode header = NULL;
int main(int ac, char * av[])
{
	PNode root = NULL;
	PNode node = make_node(5, 'a');
	root = insert_node(root, node);
	node = make_node(3, 'b');
	root = insert_node(root, node);
	node = make_node(6, 'c');
	root = insert_node(root, node);
	node = make_node(2, 'd');
	root = insert_node(root, node);
	node = make_node(4, 'e');
	root = insert_node(root, node);
	node = make_node(7, 'f');
	root = insert_node(root, node);
	in_order(root);
	return 0;
}
PNode make_node(unsigned key, char value)
{
	PNode node = (PNode)(malloc(sizeof(Node)));
	if (node)
	{
		node->_key = key;
		node->_value = value;
		node->_left = NULL;
		node->_right = NULL;
	}
	return node;
}
PNode insert_node(PNode root, PNode node)
{
	if (!root)
	{
		return node;
	}
	if (root->_key == node->_key)
	{
		root->_value = node->_value;
	}
	else if (root->_key > node->_key)
	{
		root->_left = insert_node(root->_left, node);
	}
	else
	{
		root->_right = insert_node(root->_right, node);
	}
	return root;
}

void visit_node(PNode node)
{
	if (!node)
		return;
	printf("%c\n", node->_value);
}
/*DFS 前序遍歷*/
void pre_order(PNode root)
{
	//終止條件
	if (!root)
		return;
	/*訪問根節點*/
	visit_node(root);
	//遍歷左子樹
	pre_order(root->_left);
	//遍歷右子樹
	pre_order(root->_right);

}
/*DFS 後序遍歷*/
void post_order(PNode root)
{
	/*終止條件*/
	if (!root)
		return;
	/*遍歷左子樹*/
	post_order(root->_left);
	/*遍歷右子樹*/
	post_order(root->_right);
	/*訪問根節點*/
	visit_node(root);
}
/*DFS中序遍歷*/
void in_order(PNode root)
{
	/*終止條件*/
	if (!root)
		return;
	/*遍歷左子樹*/
	in_order(root->_left);
	/*訪問根節點*/
	visit_node(root);
	/*遍歷右子樹*/
	in_order(root->_right);
}

廣度優先遍歷

#include <stdio.h>
#include <stdlib.h>
typedef struct _Node
{
	unsigned _key;
	char _value;
	struct _Node * _left;
	struct _Node * _right;
} Node, *PNode;

typedef struct _QueueNode
{
	struct _QueueNode * next;
	PNode value;
} QueueNode, *PQueueNode;

PQueueNode queue_header = NULL;
void push(PQueueNode queue_node)
{
	if (!queue_node)
	{
		return;
	}
	if (!queue_header)
	{
		queue_header = queue_node;
		return;
	}
	PQueueNode next_node = queue_header;
	while (next_node->next)
	{
		next_node = next_node->next;
	}
	next_node->next = queue_node;
}
PQueueNode pop(void)
{
	if (!queue_header)
	{
		return NULL;
	}
	PQueueNode node = queue_header;
	queue_header = queue_header->next;
	return node;
}
PQueueNode make_queue_node(PNode value)
{
	if (!value)
	{
		return NULL;
	}
	PQueueNode node = (PQueueNode)(malloc(sizeof(QueueNode)));
	node->next = NULL;
	node->value = value;
	return node;
}
bool has_next(void)
{
	return queue_header;
}
PNode make_node(unsigned key,char value)
{
	PNode node = (PNode)(malloc(sizeof(Node)));
	if (node)
	{
		node->_key = key;
		node->_value = value;
		node->_left = NULL;
		node->_right = NULL;
	}
	return node;
}

PNode insert_node(PNode root, PNode node)
{
	if (!root)
	{
		return node;
	}
	if (root->_key==node->_key)
	{
		root->_value = node->_value;
	}
	else if (root->_key>node->_key)
	{
		root->_left = insert_node(root->_left, node);
	}
	else
	{
		root->_right = insert_node(root->_right, node);
	}
	return root;
}
void visit_node(PNode node)
{
	if (!node)
		return;
	printf("%c\n", node->_value);
}
void visit_BFS(PNode root)
{
	if (!root)
	{
		return;
	}
	push(make_queue_node(root));
	while (has_next())
	{
		PQueueNode queue_node = pop();
		PNode tree_node = queue_node->value;
		visit_node(tree_node);
		push(make_queue_node(tree_node->_left));
		push(make_queue_node(tree_node->_right));
		free(queue_node);
		queue_node = NULL;
	}
}

int main(void)
{
	PNode root = NULL;
	PNode node = make_node(5, 'a');
	root = insert_node(root, node);
	node = make_node(3, 'b');
	root = insert_node(root, node);
	node = make_node(6, 'c');
	root = insert_node(root, node);
	node = make_node(2, 'd');
	root = insert_node(root, node);
	node = make_node(4, 'e');
	root = insert_node(root, node);
	node = make_node(7, 'f');
	root = insert_node(root, node);
	visit_BFS(root);
	return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章