Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
So I was write as I suspected; the grid is not actually being built like I thought it was. Sure the ID's print fine but when the grid positions are procedurally accessed the program fails with IndexError. python3 test1.py | 19 | 5 | 5 | 5 | | 11 | 6 | 19 | 11 | | 6 | 6 | 11 | 19 | | 11 | 20 | 6 | 5 | | 11 | 5 | 20 | 5 | | 20 | 20 | 11 | 11 | | 19 | 19 | 5 | 5 | | 11 | 19 | 19 | 5 | After Eliminations | 0 | 0 | 0 | 5 | | 11 | 0 | 19 | 11 | | 0 | 0 | 11 | 0 | | 0 | 20 | 6 | 0 | | 0 | 5 | 20 | 0 | | 0 | 0 | 0 | 0 | | 19 | 0 | 0 | 0 | | 0 | 0 | 0 | 0 | broke 0 5 0 6 broke 1 6 1 7 broke 2 6 2 7 broke 3 6 3 7 After Drops | 0 | 0 | 0 | 5 | | 0 | 0 | 19 | 0 | | 0 | 0 | 11 | 0 | | 0 | 20 | 6 | 0 | | 0 | 0 | 0 | 0 | | 0 | 0 | 0 | 0 | | 11 | 0 | 0 | 0 | | 19 | 5 | 20 | 11 | Normal | 0,0 | 1,0 | 2,0 | 3,0 | | 0,1 | 1,1 | 2,1 | 3,1 | | 0,2 | 1,2 | 2,2 | 3,2 | | 0,3 | 1,3 | 2,3 | 3,3 | | 0,4 | 1,4 | 2,4 | 3,4 | | 0,5 | 1,5 | 2,5 | 3,5 | | 0,6 | 1,6 | 2,6 | 3,6 | | 0,7 | 1,7 | 2,7 | 3,7 | Procedurally # The first printed pair is the id, the second pair in parentheses is # the procedurally accessed id, which should be all ordered as (column, # row) | 0,0 (0,0) | 1,0 (0,1) | 2,0 (0,2) | 3,0 (0,3) | Traceback (most recent call last): File "test1.py", line 186, in grid.draw_by_id_proc() File "test1.py", line 75, in draw_by_id_proc print(self.grid[col_num][row_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ') IndexError: list index out of range I am attempting to fix it now. Any help is appreciated. #Code Below import random class GameTile(): def __init__(self, col, row, values=None, value=None, **kwargs): # values is not required because the value can be directly set. # This is to support a future feature that will allow me to build a # board off of a list. # id is grid (X,Y) which is equal to grid (col,row) self.id = str(col) + ',' + str(row) self.col = col self.row = row if value is None: value = random.choice(values) self.value = value self.eliminated = False # hide_anim = hidden for animation purposes self.hide_anim = False # drop_value = value to be dropped during animation self.drop_value = None # drop_to could have inversely been a drop_from # drop_to = the id of where the value should be dropped too. self.drop_to = None def __str__(self): return "%2d" % self.value class GameGrid(): def __init__(self, cols=8, rows=7, **kwargs): if cols < 3 or rows < 3: raise ValueError("Minimum board size is 3x3! %sx%s is too small." % (cols, rows)) self.cols = cols self.rows = rows self.values = [5, 6, 11, 19, 20] self.make_grid() def make_grid(self): # grid is 2d array as x, y ie [x][y]. self.grid = [] for row_num in range(self.rows): # Do you still think this needs to be broken into a smaller method? row = [GameTile(col_num, row_num, self.values) for col_num in range(self.cols)] self.grid.append(row) self.transposed_grid = list(zip(*self.grid)) def draw(self): for col in self.grid: print(end='| ') for node in col: print(node, end=' | ') print() def draw_by_id(self): for col in self.grid: print(end='| ') for node in col: print(node.id, end=' | ') print() def draw_by_id_trans(self): for col in self.transposed_grid: print(end='| ') for node in col: print(node.id, end=' | ') print() def draw_by_id_proc(self): # Draw Procedurally for col_num in range(self.cols): print(end='| ') for row_num in range(self.rows): print(self.grid[col_num][row_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ') print() def find_eliminations(self): #First Down the columns. i = 0 for col_list in self.transposed_grid: while True: try: if self.check_total(col_list[i: i + 3]): self.eliminate(col_list[i: i + 3]) i += 1 except ValueError: i = 0 break # Now across the rows. for row_list in self.grid: while True: try: if self.check_total(row_list[i: i + 3]): self.eliminate(row_list[i: i + 3]) i += 1 except ValueError: i = 0 break # Set all eliminated nodes to a value of 0. for col in self.grid:
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
Now I have the output that I expect and procedurally they output matches the id of the Node/Tile. But I am thoroughly confused as to why my by_id functions use the opposite grid to get the correct output? # Output python3 test1.py | 6 | 20 | 19 | 11 | 11 | 20 | 5 | 11 | | 20 | 19 | 20 | 11 | 11 | 19 | 19 | 20 | | 6 | 19 | 19 | 6 | 5 | 20 | 5 | 11 | | 11 | 5 | 5 | 11 | 11 | 6 | 6 | 5 | By ID | 0,0 | 1,0 | 2,0 | 3,0 | | 0,1 | 1,1 | 2,1 | 3,1 | | 0,2 | 1,2 | 2,2 | 3,2 | | 0,3 | 1,3 | 2,3 | 3,3 | | 0,4 | 1,4 | 2,4 | 3,4 | | 0,5 | 1,5 | 2,5 | 3,5 | | 0,6 | 1,6 | 2,6 | 3,6 | | 0,7 | 1,7 | 2,7 | 3,7 | Procedurally | 0,0 (0,0) | 1,0 (1,0) | 2,0 (2,0) | 3,0 (3,0) | | 0,1 (0,1) | 1,1 (1,1) | 2,1 (2,1) | 3,1 (3,1) | | 0,2 (0,2) | 1,2 (1,2) | 2,2 (2,2) | 3,2 (3,2) | | 0,3 (0,3) | 1,3 (1,3) | 2,3 (2,3) | 3,3 (3,3) | | 0,4 (0,4) | 1,4 (1,4) | 2,4 (2,4) | 3,4 (3,4) | | 0,5 (0,5) | 1,5 (1,5) | 2,5 (2,5) | 3,5 (3,5) | | 0,6 (0,6) | 1,6 (1,6) | 2,6 (2,6) | 3,6 (3,6) | | 0,7 (0,7) | 1,7 (1,7) | 2,7 (2,7) | 3,7 (3,7) | Tansposed | 0,0 | 0,1 | 0,2 | 0,3 | 0,4 | 0,5 | 0,6 | 0,7 | | 1,0 | 1,1 | 1,2 | 1,3 | 1,4 | 1,5 | 1,6 | 1,7 | | 2,0 | 2,1 | 2,2 | 2,3 | 2,4 | 2,5 | 2,6 | 2,7 | | 3,0 | 3,1 | 3,2 | 3,3 | 3,4 | 3,5 | 3,6 | 3,7 | Transposed & Procedurally | 0,0 (0,0) | 0,1 (0,1) | 0,2 (0,2) | 0,3 (0,3) | 0,4 (0,4) | 0,5 (0,5) | 0,6 (0,6) | 0,7 (0,7) | | 1,0 (1,0) | 1,1 (1,1) | 1,2 (1,2) | 1,3 (1,3) | 1,4 (1,4) | 1,5 (1,5) | 1,6 (1,6) | 1,7 (1,7) | | 2,0 (2,0) | 2,1 (2,1) | 2,2 (2,2) | 2,3 (2,3) | 2,4 (2,4) | 2,5 (2,5) | 2,6 (2,6) | 2,7 (2,7) | | 3,0 (3,0) | 3,1 (3,1) | 3,2 (3,2) | 3,3 (3,3) | 3,4 (3,4) | 3,5 (3,5) | 3,6 (3,6) | 3,7 (3,7) | # Code Below import random class GameTile(): def __init__(self, col, row, values=None, value=None, **kwargs): # values is not required because the value can be directly set. # This is to support a future feature that will allow me to build a # board off of a list. # id is grid (X,Y) which is equal to grid (col,row) self.id = str(col) + ',' + str(row) self.col = col self.row = row if value is None: value = random.choice(values) self.value = value self.eliminated = False # hide_anim = hidden for animation purposes self.hide_anim = False # drop_value = value to be dropped during animation self.drop_value = None # drop_to could have inversely been a drop_from # drop_to = the id of where the value should be dropped too. self.drop_to = None def __str__(self): return "%2d" % self.value class GameGrid(): def __init__(self, cols=8, rows=7, **kwargs): if cols < 3 or rows < 3: raise ValueError("Minimum board size is 3x3! %sx%s is too small." % (cols, rows)) self.cols = cols self.rows = rows self.values = [5, 6, 11, 19, 20] self.make_grid() def make_grid(self): # grid is 2d array as x, y ie [x][y]. self.transposed_grid = [] for row_num in range(self.rows): # Do you still think this needs to be broken into a smaller method? row = [GameTile(col_num, row_num, self.values) for col_num in range(self.cols)] self.transposed_grid.append(row) self.grid = list(zip(*self.transposed_grid)) def draw(self): for row in self.grid: print(end='| ') for node in row: print(node, end=' | ') print() def draw_by_id(self): # Why does this one use self.transposed_grid instead of self.grid ? for row in self.transposed_grid: print(end='| ') for node in row: print(node.id, end=' | ') print() def draw_by_id_proc(self): # Draw Procedurally for row_num in range(self.rows): print(end='| ') for col_num in range(self.cols): print(self.grid[col_num][row_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ') print() def draw_by_id_trans(self): # Why does this one use self.grid instead of self.transposed_grid ? for col in self.grid: print(end='| ') for node in col: print(node.id, end=' | ') print() def draw_by_id_proc_trans(self): # Draw Procedurally & Transposed for col_num in range(self.cols): print(end='| ') for row_num in range(self.rows): print(self.transposed_grid[row_num][col_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ') print() def find_eliminations(self): #First Down the columns. i = 0 for col_list in self.transposed_grid: while True: try: if self.check_total(col_list[i: i + 3]): self.eliminate(co
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
I fixed the other functions to again work as expected. But the procedural access of the self.grid and self.transposed_grid also function correctly. That is good because now I can again do lookups if I need to. Although I do not have a need to at this time. Can anyone see anything wrong with the logic as it is at this time? If anyone has any improvements or things to think about, I would love to hear it. I am going to work on some tests that will specifically involve the procedural code to verify that the id's are arranged in the grid as I expect them to be. I would also appreciate an explanation of why my by_id functions use the opposite grid to get the correct output? #Output Below python3 test1.py | 19 | 11 | 5 | 19 | | 11 | 19 | 19 | 5 | | 20 | 19 | 20 | 6 | | 11 | 19 | 11 | 5 | | 11 | 6 | 5 | 20 | | 6 | 5 | 19 | 19 | | 20 | 19 | 20 | 20 | | 6 | 20 | 19 | 20 | After Eliminations | 19 | 0 | 5 | 19 | | 0 | 0 | 0 | 5 | | 0 | 0 | 20 | 6 | | 0 | 19 | 11 | 5 | | 0 | 6 | 5 | 20 | | 0 | 5 | 19 | 19 | | 20 | 19 | 20 | 20 | | 6 | 20 | 19 | 20 | After Drops | 0 | 0 | 0 | 19 | | 0 | 0 | 5 | 5 | | 0 | 0 | 20 | 6 | | 0 | 19 | 11 | 5 | | 0 | 6 | 5 | 20 | | 19 | 5 | 19 | 19 | | 20 | 19 | 20 | 20 | | 6 | 20 | 19 | 20 | By ID | 0,0 | 1,0 | 2,0 | 3,0 | | 0,1 | 1,1 | 2,1 | 3,1 | | 0,2 | 1,2 | 2,2 | 3,2 | | 0,3 | 1,3 | 2,3 | 3,3 | | 0,4 | 1,4 | 2,4 | 3,4 | | 0,5 | 1,5 | 2,5 | 3,5 | | 0,6 | 1,6 | 2,6 | 3,6 | | 0,7 | 1,7 | 2,7 | 3,7 | Procedurally | 0,0 (0,0) | 1,0 (1,0) | 2,0 (2,0) | 3,0 (3,0) | | 0,1 (0,1) | 1,1 (1,1) | 2,1 (2,1) | 3,1 (3,1) | | 0,2 (0,2) | 1,2 (1,2) | 2,2 (2,2) | 3,2 (3,2) | | 0,3 (0,3) | 1,3 (1,3) | 2,3 (2,3) | 3,3 (3,3) | | 0,4 (0,4) | 1,4 (1,4) | 2,4 (2,4) | 3,4 (3,4) | | 0,5 (0,5) | 1,5 (1,5) | 2,5 (2,5) | 3,5 (3,5) | | 0,6 (0,6) | 1,6 (1,6) | 2,6 (2,6) | 3,6 (3,6) | | 0,7 (0,7) | 1,7 (1,7) | 2,7 (2,7) | 3,7 (3,7) | Tansposed | 0,0 | 0,1 | 0,2 | 0,3 | 0,4 | 0,5 | 0,6 | 0,7 | | 1,0 | 1,1 | 1,2 | 1,3 | 1,4 | 1,5 | 1,6 | 1,7 | | 2,0 | 2,1 | 2,2 | 2,3 | 2,4 | 2,5 | 2,6 | 2,7 | | 3,0 | 3,1 | 3,2 | 3,3 | 3,4 | 3,5 | 3,6 | 3,7 | Transposed & Procedurally | 0,0 (0,0) | 0,1 (0,1) | 0,2 (0,2) | 0,3 (0,3) | 0,4 (0,4) | 0,5 (0,5) | 0,6 (0,6) | 0,7 (0,7) | | 1,0 (1,0) | 1,1 (1,1) | 1,2 (1,2) | 1,3 (1,3) | 1,4 (1,4) | 1,5 (1,5) | 1,6 (1,6) | 1,7 (1,7) | | 2,0 (2,0) | 2,1 (2,1) | 2,2 (2,2) | 2,3 (2,3) | 2,4 (2,4) | 2,5 (2,5) | 2,6 (2,6) | 2,7 (2,7) | | 3,0 (3,0) | 3,1 (3,1) | 3,2 (3,2) | 3,3 (3,3) | 3,4 (3,4) | 3,5 (3,5) | 3,6 (3,6) | 3,7 (3,7) | # Code Below import random class GameTile(): def __init__(self, col, row, values=None, value=None, **kwargs): # values is not required because the value can be directly set. # This is to support a future feature that will allow me to build a # board off of a list. # id is grid (X,Y) which is equal to grid (col,row) self.id = str(col) + ',' + str(row) self.col = col self.row = row if value is None: value = random.choice(values) self.value = value self.eliminated = False # hide_anim = hidden for animation purposes self.hide_anim = False # drop_value = value to be dropped during animation self.drop_value = None # drop_to could have inversely been a drop_from # drop_to = the id of where the value should be dropped too. self.drop_to = None def __str__(self): return "%2d" % self.value class GameGrid(): def __init__(self, cols=8, rows=7, **kwargs): if cols < 3 or rows < 3: raise ValueError("Minimum board size is 3x3! %sx%s is too small." % (cols, rows)) self.cols = cols self.rows = rows self.values = [5, 6, 11, 19, 20] self.make_grid() def make_grid(self): # grid is 2d array as x, y ie [x][y]. self.transposed_grid = [] for row_num in range(self.rows): # Do you still think this needs to be broken into a smaller method? row = [GameTile(col_num, row_num, self.values) for col_num in range(self.cols)] self.transposed_grid.append(row) self.grid = list(zip(*self.transposed_grid)) def draw(self): for row in self.transposed_grid: print(end='| ') for node in row: print(node, end=' | ') print() def draw_by_id(self): # Why does this one use self.transposed_grid instead of self.grid ? for row in self.transposed_grid: print(end='| ') for node in row: print(node.id, end=' | ') print() def draw_by_id_proc(self): # Draw Procedurally for row_num in range(self.rows): print(end='| ') for col_num in range(self.cols): print(self.grid[col_num][row_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ')
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
On 12/01/2015 19:35, WolfRage wrote: So I was write as I suspected; the grid is not actually being built like I thought it was. Sure the ID's print fine but when the grid positions are procedurally accessed the program fails with IndexError. python3 test1.py | 19 | 5 | 5 | 5 | | 11 | 6 | 19 | 11 | | 6 | 6 | 11 | 19 | | 11 | 20 | 6 | 5 | | 11 | 5 | 20 | 5 | | 20 | 20 | 11 | 11 | | 19 | 19 | 5 | 5 | | 11 | 19 | 19 | 5 | After Eliminations | 0 | 0 | 0 | 5 | | 11 | 0 | 19 | 11 | | 0 | 0 | 11 | 0 | | 0 | 20 | 6 | 0 | | 0 | 5 | 20 | 0 | | 0 | 0 | 0 | 0 | | 19 | 0 | 0 | 0 | | 0 | 0 | 0 | 0 | broke 0 5 0 6 broke 1 6 1 7 broke 2 6 2 7 broke 3 6 3 7 After Drops | 0 | 0 | 0 | 5 | | 0 | 0 | 19 | 0 | | 0 | 0 | 11 | 0 | | 0 | 20 | 6 | 0 | | 0 | 0 | 0 | 0 | | 0 | 0 | 0 | 0 | | 11 | 0 | 0 | 0 | | 19 | 5 | 20 | 11 | Normal | 0,0 | 1,0 | 2,0 | 3,0 | | 0,1 | 1,1 | 2,1 | 3,1 | | 0,2 | 1,2 | 2,2 | 3,2 | | 0,3 | 1,3 | 2,3 | 3,3 | | 0,4 | 1,4 | 2,4 | 3,4 | | 0,5 | 1,5 | 2,5 | 3,5 | | 0,6 | 1,6 | 2,6 | 3,6 | | 0,7 | 1,7 | 2,7 | 3,7 | Procedurally # The first printed pair is the id, the second pair in parentheses is # the procedurally accessed id, which should be all ordered as (column, # row) | 0,0 (0,0) | 1,0 (0,1) | 2,0 (0,2) | 3,0 (0,3) | Traceback (most recent call last): File "test1.py", line 186, in grid.draw_by_id_proc() File "test1.py", line 75, in draw_by_id_proc print(self.grid[col_num][row_num].id, '(' + str(col_num) + ',' + str(row_num) + ')', end=' | ') IndexError: list index out of range I haven't looked carefully at your code but there's always a smell in Python when you see structure[x][y]. Can you change the grid so you always write something like:- for row in grid: for cell in row: process(cell) I say this as I'm all for short term pain, long term gain, especially when it's guaranteed to eliminate "list index out of range" errors. -- My fellow Pythonistas, ask not what our language can do for you, ask what you can do for our language. Mark Lawrence ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: https://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
On 12/01/15 20:28, WolfRage wrote: anyone has any improvements or things to think about, I would love to hear it. Sorry, no time to read the detail, but one thing I thought might be handy is to convert the draw method to return a string and make it the __str__methodf of the grid. Then the draw method becomes print(self) And you can also just use print(aGrid) etc. Something like (untested): def __str__(self): output = [] for row in self.transposed_grid: s='| ' for node in row: s += (str(node) + ' | ') output.append(s) return '\n'.join(output) def draw(self): print (self) Just a thought. -- Alan G Author of the Learn to Program web site http://www.alan-g.me.uk/ http://www.amazon.com/author/alan_gauld Follow my photo-blog on Flickr at: http://www.flickr.com/photos/alangauldphotos ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: https://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
I haven't looked carefully at your code but there's always a smell in Python when you see structure[x][y]. Can you change the grid so you always write something like:- for row in grid: for cell in row: process(cell) I say this as I'm all for short term pain, long term gain, especially when it's guaranteed to eliminate "list index out of range" errors. I think in this case I have to say no. I purposely wrote those "proc" or "procedurally" style functions to ensure that access to the grid in this way would result in the correct output from id, and to test that it worked as expected. However there are other places in my code where I think I can eliminate this smell such as the new function that drops the non-zero values. ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: https://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
On 01/12/2015 05:00 PM, Alan Gauld wrote: Sorry, no time to read the detail, but one thing I thought might be handy is to convert the draw method to return a string and make it the __str__methodf of the grid. Then the draw method becomes print(self) And you can also just use print(aGrid) etc. Something like (untested): def __str__(self): output = [] for row in self.transposed_grid: s='| ' for node in row: s += (str(node) + ' | ') output.append(s) return '\n'.join(output) def draw(self): print (self) Just a thought. OK. I will implement this, thanks. It goes well with the __str__ method of the tiles/nodes. ___ Tutor maillist - Tutor@python.org To unsubscribe or change subscription options: https://mail.python.org/mailman/listinfo/tutor
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
On 01/12/2015 05:00 PM, Alan Gauld wrote: __str__methodf of the grid. Then the draw method becomes print(self) And you can also just use print(aGrid) etc. Implemented with some other improvements using the same idea but applied to several of the other functions, that provide output. Now I am going to try and add the ability to have the table generated but with a set number of rows empty or pre-set to zero. #CODE BELOW import random class GameTile(): def __init__(self, col, row, values=None, value=None, **kwargs): # values is not required because the value can be directly set. # This is to support a future feature that will allow me to build a # board off of a list. # id is grid(X,Y) which is equal to grid(col,row) self.id = str(col) + ',' + str(row) self.col = col self.row = row if value is None: value = random.choice(values) self.value = value self.eliminated = False # hide_anim = hidden for animation purposes self.hide_anim = False # drop_value = value to be dropped during animation self.drop_value = None # drop_to could have inversely been a drop_from # drop_to = the id of where the value should be dropped too. self.drop_to = None def __str__(self): return "%2d" % self.value class GameGrid(): def __init__(self, cols=8, rows=7, **kwargs): if cols < 3 or rows < 3: raise ValueError("Minimum board size is 3x3! %sx%s is too small." % (cols, rows)) self.cols = cols self.rows = rows self.values = [5, 6, 11, 19, 20] self.make_grid() def __str__(self): output = [] for row in self.transposed_grid: s = '| ' for node in row: s += str(node) + ' | ' output.append(s) return '\n'.join(output) def make_grid(self): # grid is 2d array as x, y ie [x][y]. # transposed_grid is 2d array as y, x ie [y][x] self.transposed_grid = [] for row_num in range(self.rows): row = [GameTile(col_num, row_num, self.values) for col_num in range(self.cols)] self.transposed_grid.append(row) self.grid = list(zip(*self.transposed_grid)) def draw(self): print(self) def draw_by_id(self): # Why does this one use self.transposed_grid instead of self.grid ? output = [] for row in self.transposed_grid: s = '| ' for node in row: s += str(node.id) + ' | ' output.append(s) return '\n'.join(output) def draw_by_id_proc(self): # Draw Procedurally output = [] for row_num in range(self.rows): s = '| ' for col_num in range(self.cols): s += (str(self.grid[col_num][row_num].id) + '(' + str(col_num) + ',' + str(row_num) + ')' + ' | ') output.append(s) return '\n'.join(output) def draw_by_id_trans(self): # Why does this one use self.grid instead of self.transposed_grid ? output = [] for col in self.grid: s = '| ' for node in col: s += str(node.id) + ' | ' output.append(s) return '\n'.join(output) def draw_by_id_trans_proc (self): # Draw Transposed & Procedurally output = [] for col_num in range(self.cols): s = '| ' for row_num in range(self.rows): s += (str(self.transposed_grid[row_num][col_num].id) + '(' + str(col_num) + ',' + str(row_num) + ')' + ' | ') output.append(s) return '\n'.join(output) def find_eliminations(self): #First Down the columns. i = 0 for col_list in self.grid: while True: try: if self.check_total(col_list[i: i + 3]): self.eliminate(col_list[i: i + 3]) i += 1 except ValueError: i = 0 break # Now across the rows. for row_list in self.transposed_grid: while True: try: if self.check_total(row_list[i: i + 3]): self.eliminate(row_list[i: i + 3]) i += 1 except ValueError: i = 0 break # Set all eliminated nodes to a value of 0. for col in self.transposed_grid: for node in col: if node.eliminated is True: node.eliminated = False node.value = 0 def check_total(self, slices): first, second, third = slices if first.value == second.value or second.value == third.value: total = first.
Re: [Tutor] Improving My Simple Game Code for Speed, Memory and Learning
Updated the code to now allow for a fill_rows optional argument for Grid, that determines how many rows are filled with values. I have also added some experimental code to invert the dropping, as in all of the values can float to the top. Other code is even more experimental and not yet working right that pulls the nodes to the right or left, with hope of being able to apply gravity in all 4 directions. But I still need to work out the bugs. Any help is greatly appreciated. Thanks for all of the contributions so far. #CODE BELOW import random class GameTile(): def __init__(self, col, row, values=None, value=None, **kwargs): # values is not required because the value can be directly set. # This is to support a future feature that will allow me to build a # board off of a list. # id is grid(X,Y) which is equal to grid(col,row) self.id = str(col) + ',' + str(row) self.col = col self.row = row if value is None: value = random.choice(values) self.value = value self.eliminated = False # hide_anim = hidden for animation purposes self.hide_anim = False # drop_value = value to be dropped during animation self.drop_value = None # drop_to could have inversely been a drop_from # drop_to = the id of where the value should be dropped too. self.drop_to = None def __str__(self): return "%2d" % self.value class GameGrid(): def __init__(self, cols=8, rows=7, fill_rows=None, **kwargs): if cols < 3 or rows < 3: raise ValueError('Minimum board size is 3x3! %sx%s is too small.' % (cols, rows)) if fill_rows > rows: string = 'Can not fill more rows than actual rows ' + \ 'exist. fill_rows=%s rows=%s' raise ValueError(string % (fill_rows, rows)) self.cols = cols self.rows = rows self.values = [5, 6, 11, 19, 20] self.make_grid(fill_rows) def __str__(self): output = [] for row in self.transposed_grid: s = '| ' for node in row: s += str(node) + ' | ' output.append(s) return '\n'.join(output) def make_grid(self, fill_rows=None): # grid is 2d array as x, y ie [x][y]. # transposed_grid is 2d array as y, x ie [y][x] self.transposed_grid = [] for row_num in range(self.rows): if fill_rows is None: values = self.values elif row_num < self.rows - fill_rows: values = [0, ] else: values = self.values row = [GameTile(col_num, row_num, values) for col_num in range(self.cols)] self.transposed_grid.append(row) self.grid = list(zip(*self.transposed_grid)) def draw(self): print(self) def draw_by_id(self): # Why does this one use self.transposed_grid instead of self.grid ? output = [] for row in self.transposed_grid: s = '| ' for node in row: s += str(node.id) + ' | ' output.append(s) return '\n'.join(output) def draw_by_id_proc(self): # Draw Procedurally output = [] for row_num in range(self.rows): s = '| ' for col_num in range(self.cols): s += (str(self.grid[col_num][row_num].id) + '(' + str(col_num) + ',' + str(row_num) + ')' + ' | ') output.append(s) return '\n'.join(output) def draw_by_id_trans(self): # Why does this one use self.grid instead of self.transposed_grid ? output = [] for col in self.grid: s = '| ' for node in col: s += str(node.id) + ' | ' output.append(s) return '\n'.join(output) def draw_by_id_trans_proc (self): # Draw Transposed & Procedurally output = [] for col_num in range(self.cols): s = '| ' for row_num in range(self.rows): s += (str(self.transposed_grid[row_num][col_num].id) + '(' + str(col_num) + ',' + str(row_num) + ')' + ' | ') output.append(s) return '\n'.join(output) def find_eliminations(self): #First Down the columns. i = 0 for col_list in self.grid: while True: try: if self.check_total(col_list[i: i + 3]): self.eliminate(col_list[i: i + 3]) i += 1 except ValueError: i = 0 break # Now across the rows. for row_list in self.transposed_grid: while True: try: if self.check_total(row_list[i: i + 3]): self.eliminate(ro