unsigned short *freq; /* priority */
};
-static int n;
-static ushort *sortptr, len_cnt[17];
-static uchar *len;
+struct tree_t {
+ ushort left[2 * NC - 1];
+ ushort right[2 * NC - 1];
+ ushort len_cnt[17];
+};
static void
-count_len(int i)
+count_len(struct tree_t *t, int i, int n, int *depth)
{ /* call with i = root */
- static int depth = 0;
-
if (i < n)
- len_cnt[(depth < 16) ? depth : 16]++;
+ t->len_cnt[(*depth < 16) ? *depth : 16]++;
else {
- depth++;
- count_len(left[i]);
- count_len(right[i]);
- depth--;
+ ++*depth;
+ count_len(t, t->left[i], n, depth);
+ count_len(t, t->right[i], n, depth);
+ --*depth;
}
}
static void
-make_len(int root)
+make_len(struct tree_t *t, int root, int n, uchar *len, ushort *sortptr)
{
int i, k;
uint cum;
+ int depth = 0;
for (i = 0; i <= 16; i++)
- len_cnt[i] = 0;
- count_len(root);
+ t->len_cnt[i] = 0;
+ count_len(t, root, n, &depth);
cum = 0;
for (i = 16; i > 0; i--)
- cum += len_cnt[i] << (16 - i);
+ cum += t->len_cnt[i] << (16 - i);
while (cum != (1U << 16)) {
- fprintf(stderr, "17");
- len_cnt[16]--;
+ t->len_cnt[16]--;
for (i = 15; i > 0; i--) {
- if (len_cnt[i] != 0) {
- len_cnt[i]--;
- len_cnt[i + 1] += 2;
+ if (t->len_cnt[i] != 0) {
+ t->len_cnt[i]--;
+ t->len_cnt[i + 1] += 2;
break;
}
}
cum--;
}
for (i = 16; i > 0; i--) {
- k = len_cnt[i];
+ k = t->len_cnt[i];
while (--k >= 0)
len[*sortptr++] = i;
}
}
static void
-make_code(int n, uchar len[], ushort code[])
+make_code(struct tree_t *t, int n, uchar len[], ushort code[])
{
int i;
ushort start[18];
start[1] = 0;
for (i = 1; i <= 16; i++)
- start[i + 1] = (start[i] + len_cnt[i]) << 1;
+ start[i + 1] = (start[i] + t->len_cnt[i]) << 1;
for (i = 0; i < n; i++)
code[i] = start[len[i]]++;
}
{
int i, j, k, avail;
struct heap_t heap;
+ struct tree_t t;
+ int n;
+ unsigned short *sortptr;
n = nparm;
heap.freq = freqparm;
- len = lenparm;
avail = n;
heap.size = 0;
heap.buf[1] = 0;
for (i = 0; i < n; i++) {
- len[i] = 0;
+ lenparm[i] = 0;
if (heap.freq[i])
heap.buf[++heap.size] = i;
}
heap.freq[k] = heap.freq[i] + heap.freq[j];
heap.buf[1] = k;
downheap(&heap, 1); /* put into queue */
- left[k] = i;
- right[k] = j;
+ t.left[k] = i;
+ t.right[k] = j;
} while (heap.size > 1);
- sortptr = codeparm;
- make_len(k);
- make_code(nparm, lenparm, codeparm);
+ make_len(&t, k, n, lenparm, codeparm);
+ make_code(&t, nparm, lenparm, codeparm);
return k; /* return root */
}