Algorithms Question Three Columns - herougo/SoftwareEngineerKnowledgeRepository GitHub Wiki
Input:
hi hello car flame
Output:
| car hi hello |
| flame |
Sort words, and print them in 3 columns in the above format.
SPOILERS BELOW
Why this is "hard" (i.e. may take more than an hour).
- handling empty entries
- coming up with
enumerate_horizontallyto reuse iterator code - proper printing
A Solution
# writing: 12:06pm - 12:29pm
# debugging: 12:29pm - 12:32pm
def enumerate_horizontally(words, num_words, start_of_each_column, empty_end_words=False):
for i in range(num_words):
column = i % NUM_COLUMNS
offset = i // NUM_COLUMNS
index = start_of_each_column[column] + offset
word = words[index]
yield index, word, column
if empty_end_words and num_words % NUM_COLUMNS > 0:
for column in range(num_words % NUM_COLUMNS, NUM_COLUMNS):
yield -1, '', column
def iter_rows(words, num_words, start_of_each_column, max_word_len_each_column):
line = ['|']
for i, word, column in enumerate_horizontally(
words, num_words, start_of_each_column, empty_end_words=True
):
if column == 0 and i != 0:
line.append('|')
yield ' '.join(line)
line = ['|']
line.append(word + ' ' * (max_word_len_each_column[column] - len(word)))
line.append('|')
yield ' '.join(line)
NUM_COLUMNS = 3
def print_columns(text):
words = text.split(' ')
words = list(sorted(words))
num_words = len(words)
num_per_column = [
(NUM_COLUMNS - 1 - i + num_words) // NUM_COLUMNS
for i in range(NUM_COLUMNS)
]
start_of_each_column = [0] * NUM_COLUMNS
for i in range(1, NUM_COLUMNS):
start_of_each_column[i] = start_of_each_column[i-1] + num_per_column[i-1]
max_word_len_each_column = [0] * NUM_COLUMNS
for i, word, column in enumerate_horizontally(words, num_words, start_of_each_column):
max_word_len_each_column[column] = max(
max_word_len_each_column[column],
len(word)
)
for row in iter_rows(words, num_words, start_of_each_column, max_word_len_each_column):
print(row)
print_columns('car bat joke cinderella')