Created
March 3, 2023 12:25
-
-
Save Chubek/0753f01ff53b2e083325441db3d13f88 to your computer and use it in GitHub Desktop.
Bitwise operations in Python on words...
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
def f_dec_to_word(dec: int) -> list[str]: | |
bits = [cBIT_ZERO] * 16 | |
i = 15 | |
while dec > 0: | |
bits[i] = str(int(dec % 2)) | |
dec //= 2 | |
i -= 1 | |
return bits | |
def f_force_uint16_overflow(dec: int) -> int: | |
bits = f_dec_to_word(dec) | |
if all([b == cBIT_ONE for b in bits]): | |
return 0 | |
return dec | |
def f_and_bit(a: str, b: str) -> str: | |
if all([binn == cBIT_ONE for binn in [a, b]]): | |
return cBIT_ONE | |
else: | |
return cBIT_ZERO | |
def f_or_bit(a: str, b: str) -> str: | |
if all([binn == cBIT_ZERO for binn in [a, b]]): | |
return cBIT_ZERO | |
return cBIT_ONE | |
def f_xor_bit(a: str, b: str) -> str: | |
if all([binn == cBIT_ONE | |
for binn in [a, b]]) or all([binn == cBIT_ZERO | |
for binn in [a, b]]): | |
return cBIT_ZERO | |
return cBIT_ONE | |
def f_not_bit(b: str) -> str: | |
return cBIT_ONE if b == cBIT_ZERO else cBIT_ZERO | |
def f_rotate_left_word(num: int, by=cMOD_ITER) -> int: | |
bits = f_dec_to_word(num) | |
left_most_bits = bits[:by] | |
right_most_bits = bits[by:] | |
rotated_bits = right_most_bits + left_most_bits | |
return int("".join(rotated_bits), 2) | |
def f_rotate_right_word(num: int, by=cMOD_ITER) -> int: | |
bits = f_dec_to_word(num) | |
left_most_bits = bits[8 - by:] | |
right_most_bits = bits[:by] | |
rotated_bits = right_most_bits + left_most_bits | |
return int("".join(rotated_bits), 2) | |
def f_shift_left_word(num: int, by: int) -> int: | |
bits = f_dec_to_word(num) | |
num_zeros = [cBIT_ZERO] * by | |
cut = bits[by:] | |
shift_left = cut + num_zeros | |
return int("".join(shift_left), 2) | |
def f_shift_right_word(num: int, by: int) -> int: | |
bits = f_dec_to_word(num) | |
num_zeros = [cBIT_ZERO] * by | |
cut = bits[:len(bits) - by] | |
shift_right = num_zeros + cut | |
return int("".join(shift_right), 2) | |
def f_and_word(a: int, b: int) -> int: | |
bits_a = f_dec_to_word(a) | |
bits_b = f_dec_to_word(b) | |
anded = [f_and_bit(aa, bb) for aa, bb in zip(bits_a, bits_b)] | |
return int("".join(anded), 2) | |
def f_or_word(a: int, b: int) -> int: | |
bits_a = f_dec_to_word(a) | |
bits_b = f_dec_to_word(b) | |
ored = [f_or_bit(aa, bb) for aa, bb in zip(bits_a, bits_b)] | |
return int("".join(ored), 2) | |
def f_xor_word(a: int, b: int) -> int: | |
bits_a = f_dec_to_word(a) | |
bits_b = f_dec_to_word(b) | |
xored = [f_xor_bit(aa, bb) for aa, bb in zip(bits_a, bits_b)] | |
return int("".join(xored), 2) | |
def f_not_word(b: int) -> int: | |
bits_b = f_dec_to_word(b) | |
notted = [f_not_bit(bb) for bb in bits_b] | |
return int("".join(notted), 2) | |
def f_reverse_complement_word(b: int) -> int: | |
bits_b = f_dec_to_word(b) | |
bits_b[0] = f_not_bit(bits_b[0]) | |
return int("".join(bits_b), 2) | |
def f_bitwise_add_words(a: int, b: int) -> int: | |
while b != 0: | |
carry = f_and_word(a, b) | |
a = f_force_uint16_overflow(f_xor_word(a, b)) | |
b = f_shift_left_word(carry, 1) | |
return a | |
def f_bitwise_sub_words(a: int, b: int) -> int: | |
b = f_bitwise_add_words(f_not_word(b), 1) | |
while b != 0: | |
carry = f_shift_left_word(f_and_word(a, b), 1) | |
a = f_force_uint16_overflow(f_xor_word(a, b)) | |
b = carry | |
return a | |
def f_bitwise_divmod_words(n: int, d: int) -> tuple[int, int]: | |
q = 0 | |
r = n | |
while r >= d: | |
q = f_bitwise_add_words(q, 1) | |
r = f_bitwise_sub_words(r, d) | |
return q, r | |
def f_bitwise_div_words(n: int, d: int) -> int: | |
return f_bitwise_divmod_words(n, d)[0] | |
def f_bitwise_mod_words(n: int, d: int) -> int: | |
return f_bitwise_divmod_words(n, d)[1] |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment