Exemple #1
0
static int Equal(TreeMap *t1,TreeMap *t2)
{
    struct Node *pt1,*pt2;
    if (t1 == t2)
    	return 1;
    if (t1 == NULL || t2 == NULL)
    	return  0;
    if (t1->count != t2->count)
    	return 0;
    if (t1->Allocator != t2->Allocator)
    	return 0;
    if (t1->compare != t2->compare)
    	return 0;
    if (t1->ElementSize != t2->ElementSize)
    	return 0;
    if (t1->Flags != t2->Flags)
    	return 0;
    pt1 = bt_first(t1);
    pt2 = bt_first(t2);
    while (pt1 && pt2) {
    	if (t1->compare(pt1->data,pt2->data,t1->aux))
    		break;
    	pt1 = bt_next(t1,pt1);
    	pt2 = bt_next(t2,pt2);
    }
    return 1;
}
Exemple #2
0
static int Save(TreeMap *src,FILE *stream, SaveFunction saveFn,void *arg)
{
    struct Node *rvp;
    if (src == NULL) {
    	iError.RaiseError("Save",CONTAINER_ERROR_BADARG);
    	return CONTAINER_ERROR_BADARG;
    }
    if (stream == NULL) {
    	src->RaiseError("Save",CONTAINER_ERROR_BADARG);
    	return CONTAINER_ERROR_BADARG;
    }
    if (saveFn == NULL) {
    	saveFn = DefaultSaveFunction;
    }
    if (fwrite(&TreeMapGuid,sizeof(guid),1,stream) <= 0)
        return EOF;
    if (arg == NULL) {
    	arg = &src->ElementSize;
    }
    if (fwrite(src,1,sizeof(TreeMap),stream) <= 0)
        return EOF;
    rvp = bt_first(src);
    while (rvp) {
    	char *p = rvp->data;

        if (saveFn(p,arg,stream) <= 0)
            return EOF;
        rvp = bt_next(src,rvp);
    }
    return 1;
}
Exemple #3
0
/* Returns the next data item in inorder
 within the tree being traversed with |trav|,
 or if there are no more data items returns |NULL|. */
static void *GetNext(Iterator *itrav)
{
    struct TreeMapIterator *trav = (struct TreeMapIterator *)itrav;

    if (trav->timestamp != trav->bst_table->timestamp)
    	return NULL;
    trav->bst_node = bt_next(trav->bst_table, trav->bst_node);
    if (trav->bst_node == NULL)
    	return NULL;
    return trav->bst_node->data;
}
Exemple #4
0
/* Moves P around in BT to compensate for its key having
   changed.  Returns a null pointer if successful.  If P's new
   value is equal to that of some other node in BT, returns the
   other node after removing P from BT.

   This function is an optimization only if it is likely that P
   can actually retain its relative position in BT, e.g. its key
   has only been adjusted slightly.  Otherwise, it is more
   efficient to simply remove P from BT, change its key, and
   re-insert P.

   It is not safe to update more than one node's key, then to
   call this function for each node.  Instead, update a single
   node's key, call this function, update another node's key, and
   so on.  Alternatively, remove all affected nodes from the
   tree, update their keys, then re-insert all of them. */
struct bt_node *
bt_changed (struct bt *bt, struct bt_node *p)
{
  struct bt_node *prev = bt_prev (bt, p);
  struct bt_node *next = bt_next (bt, p);

  if ((prev != NULL && bt->compare (prev, p, bt->aux) >= 0)
      || (next != NULL && bt->compare (p, next, bt->aux) >= 0))
    {
      bt_delete (bt, p);
      return bt_insert (bt, p);
    }
  return NULL;
 }
Exemple #5
0
int
bt_seek(BTREE * bt, void *op, void *key)
{
   u4 *node = &bt->root;

   int r = 0;

   while (*node)
   {
      r = bt->bt_compare(op, key, (void *) ((uchar *) NODE(*node) + sizeof(BT_NODE)), NULL);
      bt->cur = *node;
      if (r == 0)
      {
	 if (!bt->unique)
	 {
	    while (!bt_prev(bt))
	    {
	       r = bt->bt_compare(op, key, bt_key(bt), NULL);
	       if (r)
	       {
		  bt_next(bt);
		  break;
	       }
	    }
	 }
	 return 1;
      }
      if (r < 0)
	 node = &(NODE(*node)->left);
      else
	 node = &(NODE(*node)->right);
   }
   if (r > 0)
      bt_next(bt);
   return 0;
}
Exemple #6
0
static TreeMap *Copy(TreeMap *src)
{
    TreeMap *result;
    struct Node *pSrc;

    if (src == NULL) {
    	iError.RaiseError("Copy",CONTAINER_ERROR_BADARG);
    	return NULL;
    }
    pSrc = bt_first(src);
    result = CreateWithAllocator(src->ElementSize,src->Allocator);
    while (pSrc) {
    	iTreeMap.Add(result,pSrc->data,NULL);
    	pSrc = bt_next(src,pSrc);
    }
    return result;
}
int
cdx_calcfiltlist(ClipMachine * ClipMachineMemory, RDD_DATA * rd, RDD_ORDER * ro, RDD_FILTER * fp, const char *__PROC__)
{
   int i, er;

   BTREE *bt;

   void *key = malloc(sizeof(unsigned int) + ro->bufsize);

   ClipVar vv, *vp;

   if (fp->list)
   {
      bt = bt_create(0, fp->listlen, sizeof(unsigned int) + ro->bufsize, _cdx_compare);
      for (i = 0; i < fp->listlen; i++)
      {
	 if ((er = rd->vtbl->rawgo(ClipMachineMemory, rd, fp->list[i], 0, __PROC__)))
	    return er;
	 if (ro->simpexpr)
	 {
	    if ((er = rd->vtbl->getvalue(ClipMachineMemory, rd, ro->simpfno, &vv, __PROC__)))
	       return er;
	    vp = &vv;
	 }
	 else
	 {
	    if ((er = rdd_calc(ClipMachineMemory, rd->area, &ro->block, &vv, 0)))
	       return er;
	    vp = _clip_vptr(&vv);
	 }
	 memcpy(key, &rd->recno, sizeof(unsigned int));
	 if ((er = cdx_formatkey(ClipMachineMemory, ro, vp, key + sizeof(unsigned int), __PROC__)))
	    return er;
	 _clip_destroy(ClipMachineMemory, &vv);
	 bt_add(bt, ro, key);
      }
      free(fp->list);
   }
   else
   {
#if 1
      unsigned int bytes = ((fp->size + 1) >> 5) + 1;

      int i, b, bb, t, tt;

      fp->listlen = 0;
      for (i = 0; i < bytes; i++)
      {
	 if (fp->rmap[i])
	 {
	    for (b = (i << 2), bb = 0; bb < 4; b++, bb++)
	    {
	       if (((char *) fp->rmap)[b])
	       {
		  for (t = (b << 3) + 1, tt = 0; tt < 8; t++, tt++)
		  {
		     if (_rm_getbit(fp->rmap, fp->size, t))
			fp->listlen++;
		  }
	       }
	    }
	 }
      }
      if (fp->listlen > 100)
      {
	 free(key);
	 return 0;
      }
#else
      fp->listlen = 0;
      for (i = 1; i <= fp->size; i++)
	 if (_rm_getbit(fp->rmap, fp->size, i))
	    fp->listlen++;
#endif
      bt = bt_create(0, fp->listlen, sizeof(unsigned int) + ro->bufsize, _cdx_compare);
#if 1
      for (i = 0; i < bytes; i++)
      {
	 if (fp->rmap[i])
	 {
	    for (b = (i << 2), bb = 0; bb < 4; b++, bb++)
	    {
	       if (((char *) fp->rmap)[b])
	       {
		  for (t = (b << 3) + 1, tt = 0; tt < 8; t++, tt++)
		  {
		     if (_rm_getbit(fp->rmap, fp->size, t))
		     {
			if ((er = rd->vtbl->rawgo(ClipMachineMemory, rd, t, 0, __PROC__)))
			   return er;
			if (ro->simpexpr)
			{
			   if ((er = rd->vtbl->getvalue(ClipMachineMemory, rd, ro->simpfno, &vv, __PROC__)))
			      return er;
			   vp = &vv;
			}
			else
			{
			   if ((er = rdd_calc(ClipMachineMemory, rd->area, &ro->block, &vv, 0)))
			      return er;
			   vp = _clip_vptr(&vv);
			}
			memcpy(key, &rd->recno, sizeof(unsigned int));
			if ((er = cdx_formatkey(ClipMachineMemory, ro, vp, key + sizeof(unsigned int), __PROC__)))
			   return er;
			_clip_destroy(ClipMachineMemory, &vv);
			bt_add(bt, ro, key);
		     }
		  }
	       }
	    }
	 }
      }
#else
      for (i = 1; i <= fp->size; i++)
      {
	 if (_rm_getbit(fp->rmap, fp->size, i))
	 {
	    if ((er = rd->vtbl->rawgo(ClipMachineMemory, rd, i, 0, __PROC__)))
	       return er;
	    if (ro->simpexpr)
	    {
	       if ((er = rd->vtbl->getvalue(ClipMachineMemory, rd, ro->simpfno, &vv, __PROC__)))
		  return er;
	       vp = &vv;
	    }
	    else
	    {
	       if ((er = rdd_calc(ClipMachineMemory, rd->area, &ro->block, &vv, 0)))
		  return er;
	       vp = _clip_vptr(&vv);
	    }
	    memcpy(key, &rd->recno, sizeof(unsigned int));
	    if ((er = cdx_formatkey(ClipMachineMemory, ro, vp, key + sizeof(unsigned int), __PROC__)))
	       return er;
	    _clip_destroy(ClipMachineMemory, &vv);
	    bt_add(bt, ro, key);
	 }
      }
#endif
   }
   fp->list = malloc(sizeof(unsigned int) * (fp->listlen + 1));
   if (!ro->descend)
   {
      bt_first(bt);
      if (bt_key(bt))
      {
	 i = 0;
	 fp->list[i] = *(unsigned int *) bt_key(bt);
	 while (!bt_next(bt))
	 {
	    i++;
	    fp->list[i] = *(unsigned int *) bt_key(bt);
	 }
      }
   }
   else
   {
      bt_last(bt);
      if (bt_key(bt))
      {
	 i = 0;
	 fp->list[i] = *(unsigned int *) bt_key(bt);
	 while (!bt_prev(bt))
	 {
	    i++;
	    fp->list[i] = *(unsigned int *) bt_key(bt);
	 }
      }
   }
   bt_destroy(bt);
   free(key);
   return 0;
}