def distribute(pattern, remainder): if len(remainder) <= 1: # if remainder is 1 join into pattern # if no remainder just return pattern return ["".join(pattern + remainder)] while remainder: for i in range(0, len(pattern)): if remainder: pattern[i] += remainder.pop() return pattern def split(pattern): """ split pattern by moving smaller sequences to remainder """ min_len = min([len(j) for j in pattern]) max_len = max([len(j) for j in pattern]) remainder = [] if max_len != min_len: while len(pattern[-1]) == min_len: remainder.append(pattern.pop()) # else means all sequences are of the same size so no remainder return pattern, remainder def euclidean_rythm(k, n): """ k hits in measure of length n """ hits = list('X' * k) silences = list('.' * (n - k)) while True: hits = distribute(hits, silences) if len(hits) == 1: return hits.pop() else: hits, silences = split(hits)