Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python - Increase recursion limit in mac osx

I have a function that its called recursively. When I run it I get the error "maximum recursion depth exceeded while calling a Python object"

How can increase the limit on mac? If I use the following, I get the error "cannot increase the limit on mac"

resource.setrlimit(resource.RLIMIT_STACK, (2**24,-1))
sys.setrecursionlimit(10**6)
like image 842
nabrugir Avatar asked Mar 17 '16 18:03

nabrugir


1 Answers

I had a problem where I had the possibility of recurring several billions of times, and the way I did it was by flattening the recursion. I don't know if this method has been documented before, because I came up with it on my own instead of finding it. All you really have to do is put the local namespace of each function in a list. This will require a change in your actual code, if there is no workaround. Here's how it works:

Say I have this function:

def flatten_a_list(obj):#[[6,5],7,[3,[9,0]]] -> [6,5,7,3,9,0]
    flattened = []
    for item in obj:
        if type(item) == list:
            flattened.append(flatten_a_list(item))
        else:
            flattened.append(item)
    return flattened

Now, this is traditionally recursive. To make it so that it will work for however many nestings there are with no limit, I would do this:

from copy import deepcopy

def improved(obj):#[[6,5],7,[3,[9,0]]] -> [6,5,7,3,9,0]
    flattened = []
    position = [0]
    while True:
        print('position: {}'.format(str(position)))
        x = deepcopy(obj)
        try:
            for index in position:
                x = x[index]
        except (IndexError, TypeError):
            break

        if type(x) == list:
            position.append(0)
            print('continuing')
            continue
        else:
            flattened.append(x)

        #Test the next position
        test = deepcopy(position)
        test[-1] += 1
        x = deepcopy(test)
        print('x: {}'.format(x))
        try:
            y = deepcopy(obj)
            for index in x:
                y = y[index]
            position = deepcopy(test)
        except (IndexError, TypeError):
            position = position[:-1]
            try:
                position[-1] += 1
            except IndexError:
                break

    return flattened

Two words: Mind Bending

The function I wrote works fine, but it is unoptimized. If you want speed, first make sure you understand the function, then combine the checkings of index overflow by taking the 'x' and 'y' blocks of code are polymorphesizing them.

You will have to adapt this to your code, but as long as you understand it, it shouldn't be much or a problem. Plus, the answer is cross platform and unlimited.

like image 159
Nick Pandolfi Avatar answered Oct 05 '22 04:10

Nick Pandolfi