Skip to content

Instantly share code, notes, and snippets.

@leonpanokarren
Created September 9, 2018 05:11
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save leonpanokarren/c7f494d579eaae04109fc9d097b60acf to your computer and use it in GitHub Desktop.
Save leonpanokarren/c7f494d579eaae04109fc9d097b60acf to your computer and use it in GitHub Desktop.
HackerLanguage Exercise solution
import re
import collections
class HackerLanguage:
def __init__(self, flag_character=':', **kwargs):
self.message = ''
self.flag_character = flag_character
def write(self, message):
self.message += message
def delete(self, delete_symbol_count):
self.message = self.message[: -1 * delete_symbol_count]
def clear(self):
self.message = ''
def send(self):
date_format = '[0-9]{2}.[0-9]{2}.[0-9]{4}'
time_format = '[0-9]{2}:[0-9]{2}[aApP][mM]'
pattern = '({})|({})'.format(date_format, time_format)
date_time_tokens = re.findall(pattern, self.message)
msg_fragment = collections.namedtuple('msg_fragment', 'text is_datetime')
message_fragments_to_encode = []
message_copy = self.message
if date_time_tokens:
for date_token, time_token in date_time_tokens:
date_time_token = date_token if date_token else time_token
# date_time_token found at the beginning of the message
if message_copy.startswith(date_time_token):
message_fragments_to_encode.append(msg_fragment(date_time_token, True))
message_copy = message_copy[len(date_time_token):]
# date_time_token found in the middle of the message
elif message_copy.index(date_time_token) > 0 and\
message_copy.index(date_time_token) + len(date_time_token) < len(message_copy):
message_fragments_to_encode.extend([
msg_fragment(message_copy[:message_copy.index(date_time_token)], False),
msg_fragment(
message_copy[
message_copy.index(date_time_token):
message_copy.index(date_time_token) + len(date_time_token)
],
True
)
]
)
message_copy = message_copy[message_copy.index(date_time_token) + len(date_time_token):]
# date_time token at the end of the message
else:
message_fragments_to_encode.extend([
msg_fragment(message_copy[:message_copy.index(date_time_token)], False),
msg_fragment(
message_copy[message_copy.index(date_time_token):],
True,
)
]
)
message_copy = ''
if not message_copy:
message_fragments_to_encode.append(msg_fragment(message_copy, False))
else:
message_fragments_to_encode.append(msg_fragment(self.message, False))
return ''.join([self.encode(fragment) for fragment in message_fragments_to_encode])
def read(self, encrypted_message):
decoded_message = ''
while encrypted_message:
if encrypted_message[0] != self.flag_character:
decoded_message += encrypted_message[0]
if len(encrypted_message) == 1:
encrypted_message = ''
else:
encrypted_message = encrypted_message[1:]
elif encrypted_message[1] == self.flag_character:
decoded_message += self.flag_character
if len(encrypted_message) == 2:
encrypted_message = ''
else:
encrypted_message = encrypted_message[2:]
elif len(encrypted_message) >= 8 and encrypted_message[1:8] == '1000000':
decoded_message += ' '
if len(encrypted_message) == 8:
encrypted_message = ''
else:
encrypted_message = encrypted_message[8:]
elif len(encrypted_message) >= 8 and re.match('^[0-9]+$', encrypted_message[1:8]):
decoded_message += chr(int(encrypted_message[1:8], 2))
if len(encrypted_message) == 8:
encrypted_message = ''
else:
encrypted_message = encrypted_message[8:]
else:
decoded_message += self.flag_character
encrypted_message = encrypted_message[1:]
return decoded_message
def encode(self, msg_fragment):
if msg_fragment.is_datetime:
return msg_fragment.text
message_fragment = msg_fragment.text.replace(self.flag_character, self.flag_character * 2)
return ''.join(
[
self.to_binary(char) if (char.isalpha() or char.isspace()) else char
for char in message_fragment
]
)
def to_binary(self, char):
return self.flag_character + (bin(ord(char))[2:] if char.isalpha() else '1000000')
if __name__ == '__main__':
#These "asserts" using only for self-checking and not necessary for auto-testing
message_1 = HackerLanguage()
message_1.write("secrit")
message_1.delete(2)
message_1.write("et")
message_2 = HackerLanguage()
assert message_1.send() == "111001111001011100011111001011001011110100"
assert message_2.read("11001011101101110000111010011101100") == "email"
print("Coding complete? Let's try tests!")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment