I would like some feedback on my red black tree implementation. Anything is fine. I've debugged this and it seems to be working fine, however I may have missed something.
Basically, this is a red black tree that stores character strings as keys and the passage that contains those strings as values. Since these keys are able to be repeated, they form a linked list as well.
TNODE *tree_add(TNODE *root, const KEY k, const VALUE v) {
LNODE *lnode = NULL;
if (root == NULL) {
TNODE *node = talloc(k);
lnode = lalloc(v);
node->head = lnode;
node->tail = lnode;
node->is_red = true;
return node;
}
if (strcmp(k, root->key) < 0) {
root->left = tree_add(root->left, k, v);
} else if (strcmp(k, root->key) > 0) {
root->right = tree_add(root->right, k, v);
} else {
if (strcmp(k, root->key) == 0) {
lnode = lalloc(v);
root->tail->next = lnode;
root->tail = lnode;
root->tail->next = NULL;
}
}
if (is_red(root->right) && !is_red(root->left)) {
root = rotate_left(root);
}
if (is_red(root->left) && is_red(root->left->left)) {
root = rotate_right(root);
}
if (is_red(root->left) && is_red(root->right)) {
flip_colors(root);
}
return root;
}
Here are TNODE and LNODE:
// LNODE is the data structure for a singly linked list.
typedef struct lnode {
VALUE val; // A pointer to the value stored in the linked list.
struct lnode *next; // Pointer to the next item in the list; it should be NULL if there is no successor.
} LNODE;
typedef struct tnode {
KEY key; // Search key for this binary search tree node.
struct tnode *right; // Right child.
struct tnode *left; // Left child.
LNODE *head; // Head of the linked list storing the values for the search key.
LNODE *tail; // Tail of the linked list storing the values for the search key.
bool is_red; // Flag use only in red-black trees to denote redness.
} TNODE;
Here are some more functions: TALLOC, LALLOC, and rotate
TNODE *talloc(const KEY k) {
TNODE *tnode = malloc(sizeof(TNODE));
if (tnode == NULL) {
return NULL;
}
tnode->key = k;
tnode->is_red = false;
tnode->head = NULL;
tnode->tail = NULL;
tnode->right = NULL;
tnode->left = NULL;
return tnode;
}
LNODE *lalloc(const VALUE v) {
LNODE *lnode = malloc(sizeof(LNODE));
if (lnode == NULL) {
return NULL;
}
lnode->val = v;
lnode->next = NULL;
return lnode;
}
TNODE *rotate_left(TNODE *h) {
TNODE *x = h->right;
h->right = x->left;
x->left = h;
x->is_red = h->is_red;
h->is_red = true;
return x;
}
TNODE *rotate_right(TNODE *h) {
TNODE *x = h->left;
h->left = x->right;
x->right = h;
x->is_red = h->is_red;
h->is_red = true;
return x;
}
void flip_colors(TNODE *h) {
h->is_red = true;
h->left->is_red = false;
h->right->is_red = false;
}