#! /usr/bin/env python3
# -*- coding: utf-8 -*-

"""
Copyright 2021, Nils Hilbricht, Germany ( https://www.hilbricht.net )

Most of this file is trivial code and does not reach the "Schaffenshöhe" for Urheberrecht. 
If it is:

This is practically intended as my Public Domain software.
However, there is no such thing as public domain in Germany.
Therefore:

Released under WTFPL License

This program is free software. It comes without any warranty, to
the extent permitted by applicable law.
You can redistribute it and/or modify it under the
terms of the Do What The Fuck You Want To Public License, Version 2,
as published by Sam Hocevar. See http://www.wtfpl.net/ for more details.
"""

def nothing(*args, **kwargs):
    pass

from functools import lru_cache #https://docs.python.org/3.4/library/functools.html#functools.lru_cache
cache_unlimited = lru_cache(maxsize=None)
#use as @cache_unlimited decorator

import itertools
def pairwise(iterable):
    "s -> (s0,s1), (s1,s2), (s2, s3), ..."
    a, b = itertools.tee(iterable)
    next(b, None)
    return zip(a, b)

def onlyOne(iterable):
    true_found = False
    for v in iterable:
        if v:
            # a True was found!
            if true_found:
                # found too many True's
                return False
            else:
                # found the first True
                true_found = True
    # found zero or one True value
    return true_found

class EndlessGenerator(object):
    """used to turn a single
    parameter into an endless list of paramters.

    DO NOT for loop over this object.
    It will never stop. Use it with next(instance)"""
    def __init__(self, value):
        self.value = value

    def __iter__(self):
        return self

    def __next__(self):
        return self.value

def flatList(lst):
    """Take a nested list of any depth and make it a flat, plain
    list with only one level"""
    for elem in lst:
        if type(elem) in (list, tuple):
            for i in flatList(elem):
                yield i
        else:
            yield elem

def compress(input, inputLowest, inputHighest, outputLowest, outputHighest):
	return (input-inputLowest) / (inputHighest-inputLowest) * (outputHighest-outputLowest) + outputLowest

def listToUniqueKeepOrder(seq):
    seen = set()
    seen_add = seen.add
    return [x for x in seq if not (x in seen or seen_add(x))]


def padhexa(self, s:str):
    """Like zfill, but for hex number strings"""
    return '0x' + s[2:].zfill(2)


import inspect
from pprint import pprint
def whoCalled():
    """If you want to use this only once, better use breakpoint()"""
    pprint (inspect.stack())
    print()


def provokecrash():
    """Obviously for testing"""
    import ctypes
    p = ctypes.pointer(ctypes.c_char.from_address(5))
    p[0] = b'x'


