+"""A mish-mash of utility functions"""
+
import string
import collections
import unicodedata
from itertools import zip_longest
-# join a a list of letters into a string
cat = ''.join
+"""join a a list of letters into a string."""
-# join a list of words into a string, separated by spaces
wcat = ' '.join
+"""join a list of words into a string, separated by spaces"""
-# join a list of lines, separated by newline
lcat = '\n'.join
+"""join a list of lines, separated by newline"""
def pos(letter):
"""Return the position of a letter in the alphabet (0-25)"""
"""Return the letter in the given position in the alphabet (mod 26)"""
return chr(number % 26 + ord('a'))
+def pad(message_len, group_len, fillvalue):
+ """Return the padding needed to extend a message to a multiple of group_len
+ in length.
+
+ fillvalue can be a function or a literal value. If a function, it is called
+ once for each padded character. Use this with fillvalue=random_english_letter
+ to pad a message with random letters.
+ """
+ padding_length = group_len - message_len % group_len
+ if padding_length == group_len: padding_length = 0
+ padding = ''
+ if callable(fillvalue):
+ for i in range(padding_length):
+ padding += fillvalue()
+ else:
+ padding += fillvalue * padding_length
+ return padding
+
def every_nth(text, n, fillvalue=''):
"""Returns n strings, each of which consists of every nth character,
starting with the 0th, 1st, 2nd, ... (n-1)th character
['abcd', 'efgh', 'i!!!']
"""
if fillvalue:
- padding = fillvalue[0] * (n - len(text) % n)
+ # padding = fillvalue[0] * (n - len(text) % n)
+ padding = pad(len(text), n, fillvalue)
+ padded_text = text + padding
else:
- padding = ''
- return [(text+padding)[i:i+n] for i in range(0, len(text), n)]
+ padded_text = text
+ return [(padded_text)[i:i+n] for i in range(0, len(text), n)]
def transpose(items, transposition):
"""Moves items around according to the given transposition
return transposed
def deduplicate(text):
+ """Return the input string, but with second (and subsequent) occurrences
+ of a character removed.
+ """
return list(collections.OrderedDict.fromkeys(text))
def index_of_coincidence(text):
+ """Index of coincidence of a string. This is low for random text,
+ higher for natural langauge.
+ """
stext = sanitise(text)
counts = collections.Counter(stext)
denom = len(stext) * (len(text) - 1) / 26