Pillow/Tests/make_hash.py

69 lines
1.3 KiB
Python
Raw Normal View History

# brute-force search for access descriptor hash table
from __future__ import print_function
modes = [
"1",
2019-06-13 18:53:42 +03:00
"L",
"LA",
"La",
"I",
"I;16",
"I;16L",
"I;16B",
"I;32L",
"I;32B",
"F",
2019-06-13 18:53:42 +03:00
"P",
"PA",
"RGB",
"RGBA",
"RGBa",
"RGBX",
"CMYK",
"YCbCr",
2019-06-13 18:53:42 +03:00
"LAB",
"HSV",
]
2014-06-25 13:25:51 +04:00
def hash(s, i):
# djb2 hash: multiply by 33 and xor character
for c in s:
2019-06-13 18:53:42 +03:00
i = (((i << 5) + i) ^ ord(c)) & 0xFFFFFFFF
return i
2014-06-25 13:25:51 +04:00
def check(size, i0):
h = [None] * size
for m in modes:
i = hash(m, i0)
i = i % size
if h[i]:
return 0
h[i] = m
return h
2018-03-03 12:54:00 +03:00
min_start = 0
# 1) find the smallest table size with no collisions
for min_size in range(len(modes), 16384):
if check(min_size, 0):
print(len(modes), "modes fit in", min_size, "slots")
break
# 2) see if we can do better with a different initial value
for i0 in range(65556):
for size in range(1, min_size):
if check(size, i0):
if size < min_size:
print(len(modes), "modes fit in", size, "slots with start", i0)
min_size = size
min_start = i0
print()
print("#define ACCESS_TABLE_SIZE", min_size)
print("#define ACCESS_TABLE_HASH", min_start)