1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44
|
#!/usr/bin/env python3
#
# This script computes the default litlen symbol costs for the near-optimal
# parser.
from math import log2
BIT_COST = 16 # Must match BIT_COST in deflate_compress.c
NUM_LEN_SLOTS = 29
print("""static const struct {
u8 used_lits_to_lit_cost[257];
u8 len_sym_cost;
} default_litlen_costs[] = {""")
MATCH_PROBS = [0.25, 0.50, 0.75]
for i, match_prob in enumerate(MATCH_PROBS):
len_prob = match_prob / NUM_LEN_SLOTS
len_sym_cost = int(-log2(len_prob) * BIT_COST)
if i == 0:
print('\t{', end='')
print(f' /* match_prob = {match_prob} */')
print('\t\t.used_lits_to_lit_cost = {')
j = 0
for num_used_literals in range(0, 257):
if num_used_literals == 0:
num_used_literals = 1
lit_prob = (1 - match_prob) / num_used_literals
lit_cost = int(-log2(lit_prob) * BIT_COST)
if j == 0:
print('\t\t\t', end='')
if j == 7 or num_used_literals == 256:
print(f'{lit_cost},')
j = 0
else:
print(f'{lit_cost}, ', end='')
j += 1
print('\t\t},')
print(f'\t\t.len_sym_cost = {len_sym_cost},')
if i < len(MATCH_PROBS) - 1:
print('\t}, {', end='')
else:
print('\t},')
print('};')
|