set python recursion limit for a function
Question: I have 2 solutions to a recursion problem that I need for a function (actually
a method). I want it to be recursive, but I want to set the recursion limit to
10 and reset it after the function is called (or not mess with recursion limit
at all). Can anyone think of a better way to do this or recommend using one
over the others? I'm leaning towards the context manager because it keeps my
code cleaner and no setting the tracebacklimit, but there might be caveats?

    
    
    import sys
    
    def func(i=1):
        print i
        if i > 10:
            import sys
            sys.tracebacklimit = 1
            raise ValueError("Recursion Limit")
        i += 1
        func(i)
    
    class recursion_limit(object):
        def __init__(self, val):
            self.val = val
            self.old_val = sys.getrecursionlimit()
        def __enter__(self):
            sys.setrecursionlimit(self.val)
        def __exit__(self, *args):
            sys.setrecursionlimit(self.old_val)
            raise ValueError("Recursion Limit")
    
    def func2(i=1):
        """
        Call as
    
        with recursion_limit(12):
            func2()
        """
        print i
        i += 1
        func2(i)
    
    if __name__ == "__main__":
        #    print 'Running func1'
        #    func()
    
        with recursion_limit(12):
            func2()
    

I do see some odd behavior though with the context manager. If I put in main

    
    
    with recursion_limit(12):
        func2()
    

It prints 1 to 10. If I do the same from the interpreter it prints 1 to 11. I
assume there is something going on under the hood when I import things?

EDIT: For posterity this is what I have come up with for a function that knows
its call depth. I doubt I'd use it in any production code, but it gets the job
done.

    
    
    import sys
    import inspect
    class KeepTrack(object):
        def __init__(self):
            self.calldepth = sys.maxint
    
        def func(self):
            zero = len(inspect.stack())
            if zero < self.calldepth:
                self.calldepth = zero
            i = len(inspect.stack())
            print i - self.calldepth
            if i - self.calldepth < 9:
                self.func()
    
    keeping_track = KeepTrack()
    keeping_track.func()
    


Answer: You shouldn't change the system recursion limit at all. You should code your
function to know how deep it is, and end the recursion when it gets too deep.

The reason the recursion limit seems differently applied in your program and
the interpreter is because they have different tops of stack: the functions
invoked in the interpreter to get to the point of running your code.

