0

I am searching a string in a BST. If I found the string, I just return it. If not found, I print 3 suggestions:

  1. the last traversed node before declaring that the node is not found
  2. the inorder successsor
  3. the inorder predecessor

My code:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>

void line() {
    printf("\n-------------------------\n");
}

typedef struct node node;

struct node {
    node* left, *right;
    char *key;
};

node *newnode(char* key) {
    node *n = malloc(sizeof(node));
    n->key = malloc(strlen(key) + 1);
    strcpy(n->key, key);
    n->right = n->left = NULL;
    return n;
}

node *insirtNode(node *root, char *key) {
    if (!root) return newnode(key);
    if (strcmp(key, root->key) < 0) {
        root->left = insirtNode(root->left, key);
    } else if (strcmp(key, root->key) > 0) {
        root->right = insirtNode(root->right, key);
    }
    return root;
}

node* search(node *root, char *key, node **pred, node **succ, node **last) {
    if (root) {
        //printf("%s:%s=%d.\n",root->key,key,strcasecmp(key,root->key));
        if (strcasecmp(key, root->key) == 0) {
            printf("%s - is correct", root->key);
            line();
            return root;
        }
        if (strcasecmp(key, root->key) < 0) { 
            if (!root->left) {
                *last = root;
            }
            *succ = root;
            return search(root->left, key, pred, succ, last);
        } else {
            if (!root->right) {
                *last = root;
            }
            *pred = root;
            return search(root->right, key, pred, succ, last);
        }
    } else return NULL;
}

int main() {
    char input[60];
    printf("enter a word:\n");
    gets(input);
    line();
    node *pred = NULL, *succ = NULL, *temp = NULL, *last = NULL;

    node *root = NULL;
    root = insirtNode(root, "anas");
    root = insirtNode(root, "anad");
    root = insirtNode(root, "anay");
    root = insirtNode(root, "anaz");
    temp = search(root, input, &pred, &succ, &last);
    if (!temp) {
        printf("%s incorrect, suggestions: %s %s %s", input, succ->key, pred->key, last->key);
    }
    printf("\n");
    return 0;
}

The functions sometimes work when the string exist in the BST. If not, it returns garbage without printing anything.

trincot
  • 317,000
  • 35
  • 244
  • 286

1 Answers1

1

There are these issues:

  • in the main function where succ->key, pred->key and last->key are accessed when any of these pointers could still be NULL.

    Not a problem, but last is likely to be equal to either succ or pred, so probably you want to avoid printing the same key twice.

    Suggested correction:

    if (temp == NULL) {
        printf("%s incorrect, suggestion(s):", input);
        if (pred != NULL) printf(" %s", pred->key);
        if (succ != NULL) printf(" %s", succ->key);
        if (last != NULL && last != pred && last != succ) printf(" %s", last->key);
    }
    
  • The call to malloc assumes that a char is a byte. This is wrong. So multiply the number of characters by sizeof(char):

    n->key = malloc((strlen(key) + 1) * sizeof(char));
    
trincot
  • 317,000
  • 35
  • 244
  • 286