commit
bc9abec31f
197
c-cpp/24_binarysearchtree/bst.c
Normal file
197
c-cpp/24_binarysearchtree/bst.c
Normal file
@ -0,0 +1,197 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <time.h>
|
||||||
|
|
||||||
|
enum child_dir {
|
||||||
|
left_child,
|
||||||
|
right_child,
|
||||||
|
root,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct node {
|
||||||
|
unsigned long data;
|
||||||
|
struct node *left;
|
||||||
|
struct node *right;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct root {
|
||||||
|
struct node *r;
|
||||||
|
};
|
||||||
|
|
||||||
|
void dump(struct node *node, int level, enum child_dir dir)
|
||||||
|
{
|
||||||
|
if (!node)
|
||||||
|
return;
|
||||||
|
|
||||||
|
dump(node->right, level + 1, right_child);
|
||||||
|
|
||||||
|
if (dir == left_child)
|
||||||
|
printf("%*s\n", level*3, "|");
|
||||||
|
|
||||||
|
printf("%*s - %05lu\n", level*3, " ", node->data);
|
||||||
|
|
||||||
|
if (dir == right_child)
|
||||||
|
printf("%*s\n", level*3, "|");
|
||||||
|
|
||||||
|
dump(node->left, level + 1, left_child);
|
||||||
|
}
|
||||||
|
|
||||||
|
struct node* find(struct root *root, unsigned long data)
|
||||||
|
{
|
||||||
|
struct node* n = root->r;
|
||||||
|
|
||||||
|
while (n) {
|
||||||
|
if (n->data == data)
|
||||||
|
return n;
|
||||||
|
if (data < n->data)
|
||||||
|
n = n->left;
|
||||||
|
else
|
||||||
|
n = n->right;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct node* new_node(unsigned long data)
|
||||||
|
{
|
||||||
|
struct node *n;
|
||||||
|
|
||||||
|
n = malloc(sizeof(struct node));
|
||||||
|
|
||||||
|
n->data = data;
|
||||||
|
n->left = n->right = NULL;
|
||||||
|
return n;
|
||||||
|
}
|
||||||
|
|
||||||
|
void insert(struct root *root, struct node *new)
|
||||||
|
{
|
||||||
|
struct node *parent;
|
||||||
|
|
||||||
|
if (!root->r) {
|
||||||
|
root->r = new;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
parent = root->r;
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
/* Don't support duplicate data */
|
||||||
|
if (new->data == parent->data)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (new->data < parent->data) {
|
||||||
|
if (!parent->left) {
|
||||||
|
parent->left = new;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
parent = parent->left;
|
||||||
|
} else {
|
||||||
|
if (!parent->right) {
|
||||||
|
parent->right = new;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
parent = parent->right;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
struct node* delete(struct root *root, unsigned long data)
|
||||||
|
{
|
||||||
|
struct node *n = root->r, **p = &root->r;
|
||||||
|
struct node *child;
|
||||||
|
|
||||||
|
while (n && n->data != data) {
|
||||||
|
if (data < n->data) {
|
||||||
|
p = &n->left;
|
||||||
|
n = n->left;
|
||||||
|
} else {
|
||||||
|
p = &n->right;
|
||||||
|
n = n->right;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!n)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if (n->left && n->right) {
|
||||||
|
struct node *rn = n->right, **rp = &n->right;
|
||||||
|
|
||||||
|
while (rn->left) {
|
||||||
|
rp = &rn->left;
|
||||||
|
rn = rn->left;
|
||||||
|
}
|
||||||
|
|
||||||
|
n->data = rn->data;
|
||||||
|
n = rn;
|
||||||
|
p = rp;
|
||||||
|
}
|
||||||
|
|
||||||
|
child = n->left ? n->left : n->right;
|
||||||
|
*p = child;
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void insert_test()
|
||||||
|
{
|
||||||
|
struct root tree;
|
||||||
|
struct node* n;
|
||||||
|
|
||||||
|
tree.r = NULL;
|
||||||
|
|
||||||
|
insert(&tree, new_node(9));
|
||||||
|
|
||||||
|
insert(&tree, new_node(5));
|
||||||
|
insert(&tree, new_node(2));
|
||||||
|
insert(&tree, new_node(8));
|
||||||
|
|
||||||
|
insert(&tree, new_node(18));
|
||||||
|
insert(&tree, new_node(13));
|
||||||
|
insert(&tree, new_node(21));
|
||||||
|
insert(&tree, new_node(20));
|
||||||
|
|
||||||
|
dump(tree.r, 0, root);
|
||||||
|
|
||||||
|
n = find(&tree, 18);
|
||||||
|
if (n && n->data == 18)
|
||||||
|
printf("Get 18\n");
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void delete_test()
|
||||||
|
{
|
||||||
|
struct root tree;
|
||||||
|
struct node* n;
|
||||||
|
|
||||||
|
tree.r = NULL;
|
||||||
|
|
||||||
|
insert(&tree, new_node(9));
|
||||||
|
|
||||||
|
insert(&tree, new_node(5));
|
||||||
|
insert(&tree, new_node(2));
|
||||||
|
insert(&tree, new_node(8));
|
||||||
|
|
||||||
|
insert(&tree, new_node(18));
|
||||||
|
insert(&tree, new_node(13));
|
||||||
|
insert(&tree, new_node(21));
|
||||||
|
insert(&tree, new_node(20));
|
||||||
|
|
||||||
|
dump(tree.r, 0, root);
|
||||||
|
|
||||||
|
delete(&tree, 20);
|
||||||
|
printf("Delete 20\n");
|
||||||
|
dump(tree.r, 0, root);
|
||||||
|
|
||||||
|
delete(&tree, 9);
|
||||||
|
printf("Delete 9\n");
|
||||||
|
dump(tree.r, 0, root);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
//insert_test();
|
||||||
|
delete_test();
|
||||||
|
return 0;
|
||||||
|
}
|
160
c-cpp/28_heap/heap.c
Normal file
160
c-cpp/28_heap/heap.c
Normal file
@ -0,0 +1,160 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <time.h>
|
||||||
|
|
||||||
|
/* Implement heap */
|
||||||
|
|
||||||
|
#define MAX_HEAP_SIZE (1 << 8)
|
||||||
|
|
||||||
|
struct element {
|
||||||
|
int data;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct heap {
|
||||||
|
union {
|
||||||
|
unsigned long elements;
|
||||||
|
struct element *elem[MAX_HEAP_SIZE];
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
void init_heap(struct heap *heap)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for(i = 0; i < MAX_HEAP_SIZE; i++) {
|
||||||
|
heap->elem[i] = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void dump_heap(struct heap *heap, int index)
|
||||||
|
{
|
||||||
|
struct element *elem;
|
||||||
|
int level;
|
||||||
|
|
||||||
|
if (index > heap->elements)
|
||||||
|
return;
|
||||||
|
|
||||||
|
elem = heap->elem[index];
|
||||||
|
level = fls(index);
|
||||||
|
|
||||||
|
dump_heap(heap, index * 2 + 1);
|
||||||
|
|
||||||
|
if (!(index % 2) && index != 1)
|
||||||
|
printf("%*s\n", level*3, "|");
|
||||||
|
|
||||||
|
printf("%*s - %05d\n", level*3, " ", elem->data);
|
||||||
|
|
||||||
|
if (index % 2 && index != 1)
|
||||||
|
printf("%*s\n", level*3, "|");
|
||||||
|
|
||||||
|
dump_heap(heap, index * 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
void dump(struct heap *heap, int elements)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 1; i <= elements; i++)
|
||||||
|
printf("[%02d]: %4d\n", i, heap->elem[i]->data);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
struct element* create_element(int data)
|
||||||
|
{
|
||||||
|
struct element *elem;
|
||||||
|
|
||||||
|
elem = malloc(sizeof(struct element));
|
||||||
|
|
||||||
|
if (elem)
|
||||||
|
elem->data = data;
|
||||||
|
|
||||||
|
return elem;
|
||||||
|
}
|
||||||
|
|
||||||
|
void fake_a_heap(struct heap *heap)
|
||||||
|
{
|
||||||
|
/* data is in ordered */
|
||||||
|
int i, data[10] = {7, 4, 9, 2, 6, 8, 10, 1, 3, 5};
|
||||||
|
|
||||||
|
init_heap(heap);
|
||||||
|
|
||||||
|
/* root start at 1 */
|
||||||
|
for (i = 0; i < 10; i++)
|
||||||
|
heap->elem[i+1] = create_element(data[i]);
|
||||||
|
|
||||||
|
heap->elements = 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
void swap(struct heap *heap, int i, int j)
|
||||||
|
{
|
||||||
|
struct element *tmp;
|
||||||
|
|
||||||
|
tmp = heap->elem[j];
|
||||||
|
heap->elem[j] = heap->elem[i];
|
||||||
|
heap->elem[i] = tmp;
|
||||||
|
}
|
||||||
|
|
||||||
|
void heapify(struct heap *heap, int parent)
|
||||||
|
{
|
||||||
|
struct element **elem = heap->elem;
|
||||||
|
int elements = heap->elements;
|
||||||
|
int left, right, max;
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
left = parent * 2;
|
||||||
|
right = left + 1;
|
||||||
|
|
||||||
|
max = parent;
|
||||||
|
if (left <= elements && elem[max]->data < elem[left]->data)
|
||||||
|
max = left;
|
||||||
|
if (right <= elements && elem[max]->data < elem[right]->data)
|
||||||
|
max = right;
|
||||||
|
|
||||||
|
if (max == parent)
|
||||||
|
break;
|
||||||
|
|
||||||
|
swap(heap, max, parent);
|
||||||
|
parent = max;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void build_heap(struct heap *heap)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = heap->elements / 2; i >= 1; i--)
|
||||||
|
heapify(heap, i);
|
||||||
|
}
|
||||||
|
|
||||||
|
int heap_sort(struct heap *heap)
|
||||||
|
{
|
||||||
|
int elements = heap->elements;
|
||||||
|
|
||||||
|
while (heap->elements) {
|
||||||
|
swap(heap, 1, heap->elements);
|
||||||
|
heap->elements--;
|
||||||
|
heapify(heap, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return elements;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
struct heap heap;
|
||||||
|
int elements;
|
||||||
|
|
||||||
|
fake_a_heap(&heap);
|
||||||
|
dump_heap(&heap, 1);
|
||||||
|
|
||||||
|
printf("After Heapify:\n");
|
||||||
|
build_heap(&heap);
|
||||||
|
dump_heap(&heap, 1);
|
||||||
|
|
||||||
|
printf("After Heap sort:\n");
|
||||||
|
elements = heap_sort(&heap);
|
||||||
|
dump(&heap, elements);
|
||||||
|
return 0;
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user