Skip to content

Instantly share code, notes, and snippets.

@bicycleprincess
Last active November 22, 2023 19:16
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save bicycleprincess/1ec87c12120643c8190495195f39af14 to your computer and use it in GitHub Desktop.
Save bicycleprincess/1ec87c12120643c8190495195f39af14 to your computer and use it in GitHub Desktop.
Hamming Code in Python with special Baudot, encoding, correcting, decoding, conventional way.
import textwrap
def list2string(data):
return ''.join(map(str, data))
# http://codegolf.stackexchange.com/questions/94056/telegraphy-golf-decode-baudot-code
SIGNS = {
"FS": "00010",
"LS": "00001",
"SP": "00011", # take fron ER
}
LETTERS = {
"A": "10000",
"B": "00110",
"C": "10110",
"D": "11110",
"E": "01000",
"F": "01110",
"G": "01010",
"H": "11010",
"I": "01100",
"J": "10010",
"K": "10011",
"L": "11011",
"M": "01011",
"N": "01111",
"O": "11100",
"P": "11111",
"Q": "10111",
"R": "00111",
"S": "00101",
"T": "10101",
"U": "10100",
"V": "11101",
"W": "01101",
"X": "01001",
"Y": "00100",
"Z": "11001"
}
FIGURES = {
"0": "11110",
"1": "10000",
"2": "01000",
"3": "00100",
"4": "10100",
"5": "11100",
"6": "10010",
"7": "01010",
"8": "00110",
"9": "10110",
"-": "00111",
"?": "01101",
":": "11001",
"(": "10011",
")": "01011",
".": "10001",
",": "00101", # take from S
"'": "11101",
"=": "11011",
"/": "11000",
"+": "11111",
"!": "11010" # take from H
}
def encodeBaudot(info):
rst = []
text = (info.upper()).split()
LC = 0 # letter count
FC = 0 # figure
for word in text:
s = []
for letter in word:
if letter in LETTERS:
if LC > 0:
s.append(LETTERS[letter])
#LC += 1
else:
s.append(SIGNS['LS'])
s.append(LETTERS[letter])
LC += 1
FC = 0
if letter in FIGURES:
if FC > 0:
s.append(FIGURES[letter])
else:
s.append(SIGNS['FS'])
s.append(FIGURES[letter])
FC += 1
LC = 0
rst.extend(s)
rst.append(SIGNS['SP'])
return rst[:-1]
def originaldecodeBaudot(s):
WORDS = []
flag_L = False
flag_F = False
data = textwrap.wrap(s, 5)
for sign in data:
if sign == SIGNS['LS']:
flag_L = True
flag_F = False
elif sign == SIGNS['FS']:
flag_F = True
flag_L = False
elif sign == SIGNS['SP']:
WORDS.extend(' ')
else:
if flag_L:
if sign in SIGNS.values():
if sign == SIGNS['FS']:
flag_L = False
flag_F = True
else:
flag_F = False
flag_L = True
else:
for letter, code in LETTERS.iteritems():
if code == sign:
WORDS.extend(letter)
elif flag_F:
if sign in SIGNS.values():
if sign == SIGNS['LS']:
flag_F = False
flag_L = True
else:
flag_F = True
flag_L = False
else:
for figure, code in FIGURES.iteritems():
if code == sign:
WORDS.extend(figure)
return list2string(WORDS)
def main():
#text = 'x=1.23 y=4.56'
text = 'helo3 me (he99he : '
info = list2string(encodeBaudot(text))
print originaldecodeBaudot(info)
if __name__ == '__main__':
main()
from baudot import *
import textwrap
def list2string(data):
return ''.join(map(str, data))
# https://en.wikipedia.org/wiki/Hamming(7,4)
zero = '0'
TABLE = {
"0000": "0000000",
"1000": "1110000",
"0100": "1001100", #0011001
"1100": "0111100", #0011110
"0010": "0101010", #0101010
"1010": "1011010", #0101101
"0110": "1100110", #0110011
"1110": "0010110", #0110100
"0001": "1101001", #1001011
"1001": "0011001", #1001100
"0101": "0100101", #1010010
"1101": "1010101", #1010101
"0011": "1000011", #1100001
"1011": "0110011", #1100110
"0111": "0001111", #1111000
"1111": "1111111"
}
def Hammingencoder(s, span=4):
en = []
if len(s) % span == 0:
data = tuple(textwrap.wrap(s, span))
for datum in data:
for origin, code in TABLE.iteritems():
if origin == datum:
en.extend(code)
else:
remainder = len(s) % span
main = s[:-remainder]
sub = s[-remainder:]
data = tuple(textwrap.wrap(main, span))
for datum in data:
for origin, code in TABLE.iteritems():
if origin == datum:
#print datum, code
en.extend(code)
en.extend(sub)
return list2string(en)
def Hammingdecoder(s, span=7):
de = []
try:
index_zero = s.index(zero*7)
amount_zero = s.count(zero*7)
string = s[index_zero:len(s)]
strings = tuple(textwrap.wrap(string, span))
for i in strings:
if len(i) == span:
for origin, code in TABLE.iteritems():
if code == i:
de.extend(origin)
else:
de.extend(i)
except ValueError:
pass
return list2string(de)
def Hammingcorrector(s, num=7):
rst = []
#p = (0,1,3)
#d = (2,4,5,6)
p1 = (0,2,4,6)
p2 = (1,2,5,6)
p4 = (3,4,5,6)
if zero*8 in s:
begin = s.index(zero*8)+1
string = s[begin:len(s)]
strings = tuple(textwrap.wrap(string, num))
for i in strings:
if len(i) == num:
t4 = parity(i, p4)
t2 = parity(i, p2)
t1 = parity(i, p1)
if t4+t2+t1 != zero*3:
index = (int(t4+t2+t1, 2)) - 1
sub = [e for e in i]
if sub[index] == zero:
sub[index] = 1
else:
sub[index] = 0
rst.extend(sub)
else:
rst.extend(i)
elif zero*num in s:
begin = s.index(zero*7)
string = s[begin:len(s)]
strings = tuple(textwrap.wrap(string, num))
for i in strings:
if len(i) == num:
t4 = parity(i, p4)
t2 = parity(i, p2)
t1 = parity(i, p1)
if t4+t2+t1 != zero*3:
index = (int(t4+t2+t1, 2)) - 1
sub = [e for e in i]
if sub[index] == zero:
sub[index] = 1
else:
sub[index] = 0
rst.extend(sub)
else:
rst.extend(i)
return list2string(rst)
#return decodeBaudot(rst)
def parity(s, indicies):
alist = [s[i] for i in indicies]
sub = ''.join(alist)
return str(str.count(sub, '1') % 2)
def main():
s = 'x=1.23 y=4.56'
baudot = list2string(encodeBaudot(s))
en = Hammingencoder(baudot)
wrong = '0000000101101010011000100101011001110100001001100010010100000001001100110100111100000001100111000001010101010101101010001010101000011011110000110010'
crct = Hammingcorrector(wrong)
de = Hammingdecoder(crct)
originaldecodeBaudot(de)
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment