Source code for unpacking_flatten_lists.funcs

"""
Examples of python realization of solution for unpacking lists with indefinite depth
"""

from typing import Iterator, Iterable, List

from iteration_utilities import deepflatten
from more_itertools import collapse


# @profile
[docs]def outer_flatten_1(array: Iterable) -> List: """ Based on C realization of this solution More on: https://iteration-utilities.readthedocs.io/en/latest/generated/deepflatten.html https://github.com/MSeifert04/iteration_utilities/blob/384948b4e82e41de47fa79fb73efc56c08549b01/src/deepflatten.c """ return deepflatten(array)
# @profile
[docs]def outer_flatten_2(array: Iterable) -> List: """ recursive algorithm, vaguely reminiscent of recursion_flatten. Based on next pattern: .. code:: python try: tree = iter(node) except TypeError: yield node more on: https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.collapse """ return collapse(array)
# @profile
[docs]def niccolum_flatten(array: Iterable) -> List: """ Non recursive algorithm Based on pop/insert elements in current list """ new_array = array[:] ind = 0 while True: try: while isinstance(new_array[ind], list): item = new_array.pop(ind) for inner_item in reversed(item): new_array.insert(ind, inner_item) ind += 1 except IndexError: break return new_array
# @profile
[docs]def tishka_flatten(data: Iterable) -> List: """ Non recursive algorithm Based on append/extend elements to new list """ nested = True while nested: new = [] nested = False for i in data: if isinstance(i, list): new.extend(i) nested = True else: new.append(i) data = new return data
# @profile
[docs]def zart_flatten(a: Iterable) -> List: """ Non recursive algorithm Based on pop from old and append elements to new list """ queue, out = [a], [] while queue: elem = queue.pop(-1) if isinstance(elem, list): queue.extend(elem) else: out.append(elem) return out[::-1]
# @profile
[docs]def recursive_flatten_generator(array: Iterable) -> List: """ Recursive algorithm Looks like recursive_flatten_iterator, but with extend/append """ lst = [] for i in array: if isinstance(i, list): lst.extend(recursive_flatten_generator(i)) else: lst.append(i) return lst
# @profile
[docs]def recursive_flatten_iterator(arr: Iterable) -> Iterator: """ Recursive algorithm based on iterator Usual solution to this problem """ for i in arr: if isinstance(i, list): yield from recursive_flatten_iterator(i) else: yield i
# @profile
[docs]def tishka_flatten_with_stack(seq: Iterable) -> List: """ Non recursive algorithm Based on zart_flatten, but build on try/except pattern """ stack = [iter(seq)] new = [] while stack: i = stack.pop() try: while True: data = next(i) if isinstance(data, list): stack.append(i) i = iter(data) else: new.append(data) except StopIteration: pass return new
def profile(): import time from unpacking_flatten_lists.data import ( generate_data, create_data_increasing_depth, create_data_decreasing_depth) all_data = generate_data() curr_data = all_data[-1][1] funcs_generated_data = [ create_data_increasing_depth, create_data_decreasing_depth ] funcs = [ outer_flatten_1, outer_flatten_2, niccolum_flatten, tishka_flatten, zart_flatten, recursive_flatten_generator, recursive_flatten_iterator, tishka_flatten_with_stack ] for func_generated_data in funcs_generated_data: creating_data = func_generated_data(**curr_data) for func in funcs: list(func(creating_data)) time.sleep(0.3) if __name__ == '__main__': profile()