From: Morton Goldberg Date: 2007-09-03T23:24:02+09:00 Subject: Re: Filling individual cells in a grid On Sep 3, 2007, at 8:40 AM, Joop Van den tillaart wrote: > Is there no one else who can help me out a bit? OK, I'll make some suggestions. 1. I think you could make your life a lot easier if you gave your cell objects more info about where they live. 2. I suggest you fill @grid with cells during initialization. 3. I suggest you include Enumerable in your Grid class. Then you only have to define Grid#each to get map, collect, and whole more for free. class Cell attr_accessor :type, :distance_road attr_reader :i def initialize(grid, i) @my_grid = grid @i = i end def xy @i.divmod(@my_grid.width).reverse end def inspect "Cell[#{@i}, #{xy.inspect}, #{type}, #{distance_road}]" end end class Grid include Enumerable attr :width, :heigh def initialize(width, height) @grid = Array.new(width * height) { |i| Cell.new(self, i) } @width = width @height = height end def [](x, y) raise IndexError.new("Index (#{x}, #{y}) out of range") \ if x < 0 || y < 0 || x >= @width || y >= @width @grid[y * width + x] end def []=(x, y, value) raise IndexError.new("Index (#{x}, #{y}) out of range") \ if x < 0 || y < 0 || x >= @width || y >= @width @grid[y * width + x] = value end def each @grid.each { |cell| yield cell } end end # Now you can do all kinds of neat things. g = Grid.new(2, 2) p g g.map { |cell| cell.type = 0; cell.distance_road = cell.i % 2 } p g h = g.select { |cell| cell.distance_road == 1 } h.each { |cell| cell.type = 42 } p g p g.any? { |cell| cell.type == 42 } p g.all? { |cell| g[*cell.xy] == cell } # # # true true Regards, Morton