for loop with recursion failing

Viewed 23

So I have been trying to make a function that gives me random co-ordinates (RAND_X, RAND_Y), then checks them against a list of previous co-ordinates (history_x, history_y), using a for loop, to make sure I haven't used them before and then update them into a list.

def get_rand(x, y, snake_length, history_x, history_y, RANDOM):
    RAND_X = random.randrange(0, x)
    RAND_Y = random.randrange(0, y)
    i = 0
    for i in range(len(snake_length)):
        if RAND_X == history_x[i] and RAND_Y == history_y[i]:
            get_rand(x, y, snake_length, history_x, history_y, RANDOM)
    RANDOM.insert(0, RAND_Y)
    RANDOM.insert(0, RAND_X)

Everything seems to go well, until I hit the recursion event. The recursion event itself happens smoothly, but then the next time I call this function the "i" value in the for-loop doesn't start from 0 and skips a couple of steps, as you can see from these terminal prints:

i: 0
RAND_X: 4
history_x: 9
RAND_Y: 4
history_y: 6
i: 1
RAND_X: 4
history_x: 9
RAND_Y: 4
history_y: 5
i: 2
RAND_X: 4
history_x: 9
RAND_Y: 4
history_y: 4
i: 3
RAND_X: 4
history_x: 8
RAND_Y: 4
history_y: 4
i: 4
RAND_X: 4
history_x: 7
RAND_Y: 4
history_y: 4
i: 5
RAND_X: 4
history_x: 6
RAND_Y: 4
history_y: 4
i: 6
RAND_X: 4
history_x: 5
RAND_Y: 4
history_y: 4
i: 7
RAND_X: 4
history_x: 4
RAND_Y: 4
history_y: 4
i: 0
RAND_X: 6
history_x: 9
RAND_Y: 2
history_y: 6
i: 1
RAND_X: 6
history_x: 9
RAND_Y: 2
history_y: 5
i: 2
RAND_X: 6
history_x: 9
RAND_Y: 2
history_y: 4
i: 3
RAND_X: 6
history_x: 8
RAND_Y: 2
history_y: 4
i: 4
RAND_X: 6
history_x: 7
RAND_Y: 2
history_y: 4
i: 5
RAND_X: 6
history_x: 6
RAND_Y: 2
history_y: 4
i: 6
RAND_X: 6
history_x: 5
RAND_Y: 2
history_y: 4
i: 7
RAND_X: 6
history_x: 4
RAND_Y: 2
history_y: 4
i: 8
RAND_X: 6
history_x: 3
RAND_Y: 2
history_y: 4
i: 9
RAND_X: 6
history_x: 3
RAND_Y: 2
history_y: 5
i: 10
RAND_X: 6
history_x: 3
RAND_Y: 2
history_y: 6
i: 11
RAND_X: 6
history_x: 4
RAND_Y: 2
history_y: 6
RANDOM: [6, 2, 9, 6, 5, 6, 7, 9, 3, 2, 8, 0, 3, 8, 6, 6, 7, 0, 8, 8, 2, 0, 7, 6, 5, 3]

i: 8
RAND_X: 4
history_x: 3
RAND_Y: 4
history_y: 4
i: 9
RAND_X: 4
history_x: 3
RAND_Y: 4
history_y: 5
i: 10
RAND_X: 4
history_x: 3
RAND_Y: 4
history_y: 6
i: 11
RAND_X: 4
history_x: 4
RAND_Y: 4
history_y: 6
RANDOM: [4, 4, 6, 2, 9, 6, 5, 6, 7, 9, 3, 2, 8, 0, 3, 8, 6, 6, 7, 0, 8, 8, 2, 0, 7, 6, 5, 3]

You can see that the value of "i" increases, until it finds a match and then starts at 0 again with a new pair of random numbers. It then goes over all the iterations and adds them to the list. However, the next time I call the function, "i" starts at 8, instead of 0. Also, it only goes up to 11 again, even though it now should go up to 12.

I hope I have explained the problem clear enough and one of you knows what I did wrong here. Pretty new to all of this.

1 Answers

The problem is your intial get_rand continues after finishing the 'recursed' get_rand You can do stop the loop by using the break statment or just returning.

You also dont need to define i for a for loop

def get_rand(x, y, snake_length, history_x, history_y, RANDOM):
    RAND_X = random.randrange(0, x)
    RAND_Y = random.randrange(0, y)
    for i in range(len(snake_length)):
        if RAND_X == history_x[i] and RAND_Y == history_y[i]:
            get_rand(x, y, snake_length, history_x, history_y, RANDOM)
            return 
            # or you use break if you have something left to do in this function
    RANDOM.insert(0, RAND_Y)
    RANDOM.insert(0, RAND_X)

A few more things

just use

RANDOM.append(RAND_X)

if it doesnt matter if your RAND_X is added at the end

Also this function is error prone due to the possibilty of infinite recursion wich will lead to a Stack overflow (you ran out of stack memory), if there is no free 'spot' in history

Furthermore youre copying the entire list(history_x, history_y) each time you call the function (or recursion is called) which might lead to bad performance for huge 2d arrays fix: try using global variables

Related