1

I have a function def next_generation(line, rule): where line is a list of booleans and rule is an integer

When you call it, it would look something like this:

>>> next_generation([True, True, True, False], 110)
[True, False, True, True]

The code takes the one before the first value (line[-1]), the first value (line[0], and the one after the first value (line[1]. Then does the same thing with the second value and so on. If that doesn't make sense here is a manual code of it that I wrote:

def next_generation(line, rule):
    
    new_gen = []

    first_cell = next_cell([line[-1], line[0], line[1]], rule)
    new_gen.append(first_cell)

    second_cell = next_cell([line[0], line[1], line[2]], rule)
    new_gen.append(second_cell)

    third_cell = next_cell([line[1], line[2], line[3]], rule)
    new_gen.append(third_cell)

    fourth_cell = next_cell([line[2], line[3], line[0]], rule)
    new_gen.append(fourth_cell)

    return new_gen

The code above works but only for a list of 4 boolean values. I want the code to do the same thing but loop through the list so it can do it for a list of any length.

Thanks in advance!

Edit:

I have now written:

def next_generation(line, rule):
    
    new_gen = []
    first_cell = next_cell([line[-1], line[0], line[1]], rule)
    new_gen.append(first_cell)
    for i in range(len(line)):
        new_gen.append(next_cell([line[i], line[i+1], line[i+2]], rule))

    last_cell = next_cell([line[-2], line[-1], line[0]], rule)
    new_gen.append(last_cell)

But it is giving me the error IndexError: list index out of range. I'm pretty sure this is happening when it says

new_gen.append(next_cell([line[i], line[i+1], line[i+2]], rule))

How should I prevent this?

4
  • 3
    try a for i in range(len(line)): and a % and let us know if you get stuck! Commented Jul 19, 2021 at 1:21
  • If your problem still exists, provide some sample i/o Commented Jul 19, 2021 at 2:00
  • how would I use the %? Commented Jul 19, 2021 at 2:06
  • Where is next_cell declared? Commented Jul 19, 2021 at 3:04

2 Answers 2

1

It looks like you're close. I believe using range(len(line) - 2), so you protect the bounds of i + 2, should resolve your IndexError.

So, then, you end up with something like the following:

def next_generation(line, rule):
    
    new_gen = []
    first_cell = next_cell([line[-1], line[0], line[1]], rule)
    new_gen.append(first_cell)

    for i in range(len(line) - 2):
        new_gen.append(next_cell([line[i], line[i + 1], line[i + 2]], rule))

    last_cell = next_cell([line[-2], line[-1], line[0]], rule)
    new_gen.append(last_cell)

Otherwise, you end up with the following execution for

next_generation([True, True, True, False], 110)
... first_cell = next_cell([line[-1], line[0], line[1]], rule)
... # Step 1 of your loop
... cell = next_cell([line[0], line[0 + 1], line[0 + 2]], rule)
... # Step 2 of your loop
... cell = next_cell([line[1], line[1 + 1], line[1 + 2]], rule)
... # Step 3 of your loop
... cell = next_cell([line[2], line[2 + 1], line[2 + 2]], rule)
...   raise IndexError(...)
Sign up to request clarification or add additional context in comments.

Comments

1

You can generate each cell using the loop:

First, let's just pretend we are still dealing with a list of 4 elements:

next_gen = []
for i in range(len(line)):
    next_gen.append(next_cell([line[i-1], line[i], line[i+1]], rule))

Now the above should produce the same output as your current program.

In order to have it work with arbitrary lines, you just need to fix the cell generation process. Again a simple loop should solve the problem:

cell_data = []
for c in range(i, len(line) + i):
    data_index = (c - 1) % len(line) if c > 0 else (c - 1)
    cell_data.append(line[data_index])

Putting it all together, we get:

next_gen = []
for i in range(len(line)):
    cell_data = []
    for c in range(i, len(line) + i):
        data_index = (c - 1) % len(line) if c > 0 else (c - 1)
        cell_data.append(line[data_index])
    next_gen.append(next_cell(cell_data, rule))

The trick with data_index is just to ensure that we only "wrap" when we are at an index greater than 0, otherwise using the modulus operator will not yield the correct results

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.