1: 
    2: 
    3:     4:     5:     6:     7:     8:     9:    10:    11:    12: 
   13: 
   14: 
   15: #include <search.h>
   16: #include <stdlib.h>
   17: 
   18: typedef struct node_t {
   19:     char          *key;
   20:     struct node_t *left, *right;
   21: } node;
   22: 
   23: 
   24: void *
   25: tsearch(const void *vkey, void **vrootp,
   26:     int (*compar)(const void *, const void *))
   27: {
   28:     node *q;
   29:     char *key = (char *)vkey;
   30:     node **rootp = (node **)vrootp;
   31: 
   32:     if (rootp == (struct node_t **)0)
   33:         return ((void *)0);
   34:     while (*rootp != (struct node_t *)0) {      
   35:         int r;
   36: 
   37:         if ((r = (*compar)(key, (*rootp)->key)) == 0)  
   38:             return ((void *)*rootp);           
   39:         rootp = (r < 0) ?
   40:             &(*rootp)->left :          
   41:             &(*rootp)->right;          
   42:     }
   43:     q = (node *) malloc(sizeof(node));  
   44:     if (q != (struct node_t *)0) {      
   45:         *rootp = q;                    
   46:         q->key = key;                  
   47:         q->left = q->right = (struct node_t *)0;
   48:     }
   49:     return ((void *)q);
   50: }
   51: 
   52: 
   53: void *
   54: tdelete(const void *vkey, void **vrootp,
   55:     int (*compar)(const void *, const void *))
   56: {
   57:     node **rootp = (node **)vrootp;
   58:     char *key = (char *)vkey;
   59:     node *p = (node *)1;
   60:     node *q;
   61:     node *r;
   62:     int cmp;
   63: 
   64:     if (rootp == (struct node_t **)0 || *rootp == (struct node_t *)0)
   65:         return ((struct node_t *)0);
   66:     while ((cmp = (*compar)(key, (*rootp)->key)) != 0) {
   67:         p = *rootp;
   68:         rootp = (cmp < 0) ?
   69:             &(*rootp)->left :          
   70:             &(*rootp)->right;          
   71:         if (*rootp == (struct node_t *)0)
   72:             return ((void *)0);                
   73:     }
   74:     r = (*rootp)->right;                        
   75:     if ((q = (*rootp)->left) == (struct node_t *)0)     
   76:         q = r;
   77:     else if (r != (struct node_t *)0) {         
   78:         if (r->left == (struct node_t *)0) {   
   79:             r->left = q;
   80:             q = r;
   81:         } else {                       
   82:             for (q = r->left; q->left != (struct node_t *)0; q = r->left)
   83:                 r = q;
   84:             r->left = q->right;
   85:             q->left = (*rootp)->left;
   86:             q->right = (*rootp)->right;
   87:         }
   88:     }
   89:     free((struct node_t *) *rootp);     
   90:     *rootp = q;                         
   91:     return(p);
   92: }
   93: 
   94: 
   95: static void
   96: trecurse(node *root, void (*action)(const void *, VISIT, int), int level)
   97: {
   98:     if (root->left == (struct node_t *)0 && root->right == (struct node_t *)0)
   99:         (*action)(root, leaf, level);
  100:     else {
  101:         (*action)(root, preorder, level);
  102:         if (root->left != (struct node_t *)0)
  103:             trecurse(root->left, action, level + 1);
  104:         (*action)(root, postorder, level);
  105:         if (root->right != (struct node_t *)0)
  106:             trecurse(root->right, action, level + 1);
  107:         (*action)(root, endorder, level);
  108:     }
  109: }
  110: 
  111: 
  112: void
  113: twalk(const void *vroot, void (*action)(const void *, VISIT, int))
  114: {
  115:     node *root = (node *)vroot;
  116: 
  117:     if (root != (node *)0 && action != (void (*)(const void *, VISIT, int))0)
  118:         trecurse(root, action, 0);
  119: }