Domanda

I've recently been trying to learn ruby using Learn to Program by Chris Pine, and at chapter 10 he gives a recursive code for counting continent size

M = 'land'
O = 'water'

world = [[O, O, O, M, O, O, O, O], 
         [O, O, M, M, O, O, M, O], 
         [M, M, M, M, M, O, O, M], 
         [M, M, O, M, O, O, O, O],
         [O, M, M, M, M, O, O, O],
         [O, O, M, M, O, M, M, M], 
         [O, O, M, O, O, O, O, O]]

def continent_size world, x, y
    if world[y][x] != M
        return 0
    end

    size = 1
    world[y][x] = 'counted'

    size += continent_size world, x-1, y-1
    size += continent_size world, x, y-1
    size += continent_size world, x+1, y-1
    size += continent_size world, x-1, y
    size += continent_size world, x+1, y
    size += continent_size world, x-1, y+1
    size += continent_size world, x, y+1
    size += continent_size world, x+1, y+
    size
end
puts continent_size world, 5, 5

in the book he states that this code would give errors if some of the land is attached to the edge (which, as you can see, I tried), but the code runs just fine. When I did try adding very simple checks, as in:

def continent_size world, x, y
    if y < 0
        return 0
    end
    if world[y][x] != M
        return 0
    end
    .
    .

suddenly I get "undefined method '[]' for nil:NilClass" error on "if world[y][x] != M" line and I really have no idea what have changed to cause this. Where is this error coming from?

edit: after some testing it does seem like the problem now is with the numbers being out of bound, since the following does work:

def continent_size (world, x, y)
    if y < 0 || y > 6 || x < 0 || x > 7
        return 0
    end
    if world[y][x] != M
        return 0
    end
    .
    .

I'm still confused as to why the original code worked with no problems though

È stato utile?

Soluzione

You have the problem with edges, if your world is 5x5 then you are calling world[6][6] against it (negative numbers still works). world[6] return nil, which does not define [] method.

To fix it, you need to add:

def continent_size world, x, y
  if y < 0 || world[y].nil? || world[y][x] != M
    return 0
  end
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top