Add decoding script

This commit is contained in:
2020-02-23 10:12:22 +00:00
parent f01a096b9c
commit 82d4b04fbc

View File

@@ -18,63 +18,88 @@ def find_node(nodes, target_character):
# if desired character not found, return empty list # if desired character not found, return empty list
return [] return []
# retrieve text to encode def encode(txt):
txt = input("Text: ") # create list of tuples in descending order of frequency: (character, frequency)
info = Counter(txt).most_common()
# change the list into ascending order
info.reverse()
# create list for character tuples
nodes = []
# create list for node usage frequencies
frequencies = []
# create list of tuples in descending order of frequency: (character, frequency) # copy nodes and their usage frequencies to the dedicated lists
info = Counter(txt).most_common() for item in info:
# change the list into ascending order nodes.append(item[0])
info.reverse() frequencies.append(item[1])
# create list for character tuples
nodes = []
# create list for node usage frequencies
frequencies = []
# copy nodes and their usage frequencies to the dedicated lists # repeat until only one top-level node exists
for item in info: while len(nodes) > 2:
nodes.append(item[0]) # combine two least frequent characters' nodes into a new tuple node, containing the old nodes (old_node_1, old_node_2)
frequencies.append(item[1]) new_node = (nodes[0], nodes[1])
# combine two least frequent characters' frequencies into a total frequency, to be used at the top level of the list of nodes
new_frequency = frequencies[0] + frequencies[1]
# remove nodes that have been nested inside the new node
del nodes[0:2]
# remove frequencies that have been summed and added to the new frequency
del frequencies[0:2]
# find index of last node with frequency below that of the new node
# if the largest frequency is smaller than the new one, place the new node at the end of the list
if (frequencies[-1] < new_frequency):
i = -1
else:
# else, loop over every frequency
for index, item in enumerate(frequencies):
# if the frequency is greater than or equal to the new frequency
if (item >= new_frequency):
# record the index to insert the frequency at
i = index
# stop looping
break
# insert the new node in its rightful position, maintaining ascending order of frequency
nodes.insert(i, new_node)
# insert the new frequency in its rightful position, maintaining ascending order of frequency
frequencies.insert(i, new_frequency)
# repeat until only one top-level node exists # print all nodes
while len(nodes) > 2: print("Nodes: %s" % nodes)
# combine two least frequent characters' nodes into a new tuple node, containing the old nodes (old_node_1, old_node_2)
new_node = (nodes[0], nodes[1]) # encrypted text
# combine two least frequent characters' frequencies into a total frequency, to be used at the top level of the list of nodes output = ""
new_frequency = frequencies[0] + frequencies[1]
# remove nodes that have been nested inside the new node # for every character in the text to be encrypted
del nodes[0:2] for char in txt:
# remove frequencies that have been summed and added to the new frequency # find its path and add it to the encrypted text
del frequencies[0:2] output += "".join(find_node(nodes, char))
# print encoded message
print("Encoded message: %s" % output)
# find index of last node with frequency below that of the new node # return encoded message
# if the largest frequency is smaller than the new one, place the new node at the end of the list return [output, nodes]
if (frequencies[-1] < new_frequency):
i = -1
else:
# else, loop over every frequency
for index, item in enumerate(frequencies):
# if the frequency is greater than or equal to the new frequency
if (item >= new_frequency):
# record the index to insert the frequency at
i = index
# stop looping
break
# insert the new node in its rightful position, maintaining ascending order of frequency
nodes.insert(i, new_node)
# insert the new frequency in its rightful position, maintaining ascending order of frequency
frequencies.insert(i, new_frequency)
# print all nodes def decode(txt, nodes):
print("Nodes: %s" % nodes) # string to hold decoded message
output = ""
# replicate nodes, for looping over and editing with the first part of the code
node = nodes
# for each digit
for digit in txt:
# get the node with the corresponding index
node = node[int(digit)]
# if the retrieved node isn't a tuple (i.e. it isn't a parent node)
if (not isinstance(node, tuple)):
# add the node's content to the output
output += node
# replace the retrieved node with the whole tree again, for looping over and editing with the next part of the code
node = nodes
# encrypted text # print decoded message
output = "" print("Decoded message: %s" % output)
# return decoded message
return output
# for every character in the text to be encrypted encoding = encode(input("Text: "))
for char in txt: decode(encoding[0], encoding[1])
# find its path and add it to the encrypted text
output += "".join(find_node(nodes, char))
# print encrypted message
print("Encrypted message: %s" % output)