Graphviz 2.29.20120208.0545
lib/cdt/dtstat.c
Go to the documentation of this file.
00001 #include        "dthdr.h"
00002 
00003 /*      Get statistics of a dictionary
00004 **
00005 **      Written by Kiem-Phong Vo (5/25/96)
00006 */
00007 
00008 #if __STD_C
00009 static void dttstat(Dtstat_t* ds, Dtlink_t* root, int depth, int* level)
00010 #else
00011 static void dttstat(ds,root,depth,level)
00012 Dtstat_t*       ds;
00013 Dtlink_t*       root;
00014 int             depth;
00015 int*            level;
00016 #endif
00017 {
00018         if(root->left)
00019                 dttstat(ds,root->left,depth+1,level);
00020         if(root->right)
00021                 dttstat(ds,root->right,depth+1,level);
00022         if(depth > ds->dt_n)
00023                 ds->dt_n = depth;
00024         if(level)
00025                 level[depth] += 1;
00026 }
00027 
00028 #if __STD_C
00029 static void dthstat(reg Dtdata_t* data, Dtstat_t* ds, reg int* count)
00030 #else
00031 static void dthstat(data, ds, count)
00032 reg Dtdata_t*   data;
00033 Dtstat_t*       ds;
00034 reg int*        count;
00035 #endif
00036 {
00037         reg Dtlink_t*   t;
00038         reg int         n, h;
00039 
00040         for(h = data->ntab-1; h >= 0; --h)
00041         {       n = 0;
00042                 for(t = data->htab[h]; t; t = t->right)
00043                         n += 1;
00044                 if(count)
00045                         count[n] += 1;
00046                 else if(n > 0)
00047                 {       ds->dt_n += 1;
00048                         if(n > ds->dt_max)
00049                                 ds->dt_max = n;
00050                 }
00051         }
00052 }
00053 
00054 #if __STD_C
00055 int dtstat(reg Dt_t* dt, Dtstat_t* ds, int all)
00056 #else
00057 int dtstat(dt, ds, all)
00058 reg Dt_t*       dt;
00059 Dtstat_t*       ds;
00060 int             all;
00061 #endif
00062 {
00063         reg int         i;
00064         static int      *Count, Size;
00065 
00066         UNFLATTEN(dt);
00067 
00068         ds->dt_n = ds->dt_max = 0;
00069         ds->dt_count = NIL(int*);
00070         ds->dt_size = dtsize(dt);
00071         ds->dt_meth = dt->data->type&DT_METHODS;
00072 
00073         if(!all)
00074                 return 0;
00075 
00076         if(dt->data->type&(DT_SET|DT_BAG))
00077         {       dthstat(dt->data,ds,NIL(int*));
00078                 if(ds->dt_max+1 > Size)
00079                 {       if(Size > 0)
00080                                 free(Count);
00081                         if(!(Count = (int*)malloc((ds->dt_max+1)*sizeof(int))) )
00082                                 return -1;
00083                         Size = ds->dt_max+1;
00084                 }
00085                 for(i = ds->dt_max; i >= 0; --i)
00086                         Count[i] = 0;
00087                 dthstat(dt->data,ds,Count);
00088         }
00089         else if(dt->data->type&(DT_OSET|DT_OBAG))
00090         {       if(dt->data->here)
00091                 {       dttstat(ds,dt->data->here,0,NIL(int*));
00092                         if(ds->dt_n+1 > Size)
00093                         {       if(Size > 0)
00094                                         free(Count);
00095                                 if(!(Count = (int*)malloc((ds->dt_n+1)*sizeof(int))) )
00096                                         return -1;
00097                                 Size = ds->dt_n+1;
00098                         }
00099 
00100                         for(i = ds->dt_n; i >= 0; --i)
00101                                 Count[i] = 0;
00102                         dttstat(ds,dt->data->here,0,Count);
00103                         for(i = ds->dt_n; i >= 0; --i)
00104                                 if(Count[i] > ds->dt_max)
00105                                         ds->dt_max = Count[i];
00106                 }
00107         }
00108         ds->dt_count = Count;
00109 
00110         return 0;
00111 }