Principle of Computing (Python)学习笔记(1) 2048

这个Principle of Computing 是Rice U在coursera上的Python课系列的第二门课。这个课的每个mini-project都是有一些小小的挑战的。
第一个mini project是实现游戏2048。

1 合并的时候每个数字只能参加一次合并。
比如,图1使用了”—>“右方向键得到图2. 注意结果不是8,是4,4。
A given tile can only merge once on any given turn
You can slide the tiles in any direction (left, right, up, or down) to move them. When you do so, if two tiles of the same number end up next to each other, they combine to form a new tile with twice the value.

Principle of Computing (Python)学习笔记(1) 2048_第1张图片                                                                

                                      图1                                                                                                                                                       图2




2 准备工作
2.1. 矩阵
http://www.codeskulptor.org/#poc_indexed_grid.py


3 test模块
3.1  学校提供的简单的UnitTest模块poc_simpletest http://www.codeskulptor.org/#poc_simpletest.py
3.2  demo,通过poc_simpletest 测试模块去测试StopWatch
http://www.codeskulptor.org/#poc_format_testsuite.py
http://www.codeskulptor.org/#poc_format_student.py


4 import 
4.1 使用import https://class.coursera.org/principlescomputing-001/wiki/view?page=imports


5 我的代码

"""

Clone of 2048 game.
"""

import poc_2048_gui        
import random

# Directions, DO NOT MODIFY
UP = 1
DOWN = 2
LEFT = 3
RIGHT = 4

# Offsets for computing tile indices in each direction.
# DO NOT MODIFY this dictionary.    
OFFSETS = {UP: (1, 0), 
           DOWN: (-1, 0), 
           LEFT: (0, 1), 
           RIGHT: (0, -1)} 

def merge(line):
    """
    Helper function that merges a single row or column in 2048
    """
    list_res = [0] * len(line)
    bool_res = [1] * len(line)
    var_j = 0
    for var_i in range(len(line)):
        if line[var_i] != 0:
            if list_res[var_j-1] == line[var_i] and bool_res[var_j-1] == 1:
                list_res[var_j-1] +=line[var_i]
                bool_res[var_j-1] = 0;
            else:
                list_res[var_j] = line[var_i]
                var_j += 1
    return list_res

class TwentyFortyEight:
    """
    Class to run the game logic.
    """

    def __init__(self, grid_height, grid_width):
        self._grid_height = grid_height
        self._grid_width = grid_width  
        self._grid = [[ 0 for dummy_i in range(self._grid_width)] for dummy_j in range(self._grid_height)] #2D矩阵初始化
        self._intial_tiles =  {
                            UP: [ (0, i) for i in range(grid_width) ],
                            DOWN: [ (grid_height-1, i) for i in range(grid_width) ],
                            LEFT: [ (i, 0) for i in range(grid_height) ],
                            RIGHT: [ (i, grid_width-1) for i in range(grid_height) ],
                            }
        self._move_helper_func = {
                       UP:self.helper_merge_up,
                       DOWN: self.helper_merge_down,
                       LEFT: self.helper_merge_left,
                       RIGHT: self.helper_merge_right,
                       }
        self._flag_changed = False;
        self.reset()        
    def reset(self):
        """
        Reset the game so the grid is empty.
        """
        for var_i in range(self._grid_height):
            for var_j in range(self._grid_width):
                self._grid[var_i][var_j]=0;
            
    def __str__(self):
        """
        Return a string representation of the grid for debugging.
        """
        res_str = "[\n"
        for var_i in range(self._grid_height):
            res_str += "["
            for var_j in range(self._grid_width):
                res_str += str(self._grid[var_i][var_j]) + ", "
            res_str += "]\n"
        res_str += "]"
        return res_str

    def get_grid_height(self):
        """
        Get the height of the board.
        """
        return self._grid_height;
    
    def get_grid_width(self):
        """
        Get the width of the board.
        """
        return self._grid_width;
                            
    def helper_merge_up(self,temp_list_new,ele):
        """
        Move the merged list to the original grid, UP direction        
        """
        for var_i in range(self.get_grid_height()):
                if self._flag_changed == False and self._grid[var_i][ele[1]] != temp_list_new[var_i]:
                    self._flag_changed  = True;
                self.set_tile(var_i,ele[1],temp_list_new[var_i])

    def helper_merge_down(self,temp_list_new,ele):
        """
        Move the merged list to the original grid, DOWN direction        
        """
        for var_i in range(self.get_grid_height()):
                if self._flag_changed == False and self._grid[self.get_grid_height()-var_i-1][ele[1]] != temp_list_new[var_i]:
                    self._flag_changed  = True;                
                self.set_tile(self.get_grid_height()-var_i-1, ele[1], temp_list_new[var_i])
        
    def helper_merge_left(self,temp_list_new,ele):
        """
        Move the merged list to the original grid, LEFT direction        
        """        
        for var_i in range(self.get_grid_width()):
                if self._flag_changed == False and self._grid[ele[0]][var_i] != temp_list_new[var_i]:
                    self._flag_changed  = True;
                self.set_tile(ele[0],var_i,temp_list_new[var_i])                    
                    
    def helper_merge_right(self,temp_list_new,ele):        
        """
        Move the merged list to the original grid, RIGHT direction        
        """        
        for var_i in range(self.get_grid_width()):
                if self._flag_changed == False and self._grid[ele[0]][self.get_grid_width()-var_i-1] != temp_list_new[var_i]:
                    self._flag_changed  = True;                
                self.set_tile(ele[0], self.get_grid_width()-var_i-1, temp_list_new[var_i])                            
        
    def move(self, direction):
        """
        Move all tiles in the given direction and add
        a new tile if any tiles moved.
        """
        self._flag_changed = False;
        for ele in self._intial_tiles[direction]:
            temp_index_list = []
            temp_list = []
            temp_index_list.append(ele);
            while temp_index_list[-1][0]>=0 and temp_index_list[-1][0]<self.get_grid_height() and temp_index_list[-1][1]>=0 and temp_index_list[-1][1]<self.get_grid_width():
                temp_list.append(self.get_tile(temp_index_list[-1][0],temp_index_list[-1][1]))    
                temp_index_list.append((temp_index_list[-1][0]+OFFSETS[direction][0],temp_index_list[-1][1]+OFFSETS[direction][1]));
            temp_list_new = merge(temp_list)
            self._move_helper_func[direction](temp_list_new,ele)        
        if  self._flag_changed :
            self.new_tile()
            
        
    def new_tile(self):
        """
        Create a new tile in a randomly selected empty 
        square.  The tile should be 2 90% of the time and
        4 10% of the time.
        """
        non_zero_count = 0;
        for var_i in range(self._grid_height):
            for var_j in range(self._grid_width):
                if self._grid[var_i][var_j] == 0:
                    non_zero_count +=1;
        random_choice = random.randrange(0,non_zero_count);
        var_k = 0
        generated_new_tile = False
        for var_i in range(self._grid_height):
            for var_j in range(self._grid_width):
                if generated_new_tile==False and self._grid[var_i][var_j] == 0:
                    if var_k != random_choice:
                        var_k += 1   
                    else:
                        random_2_4 = random.randrange(0,100)
                        if random_2_4 <10:
                            self.set_tile(var_i,var_j,4)
                        else:
                            self.set_tile(var_i,var_j,2)
                        generated_new_tile = True;
      
        
    def set_tile(self, row, col, value):
        """
        Set the tile at position row, col to have the given value.
        """        
        self._grid[row][col] = value;

    def get_tile(self, row, col):
        """
        Return the value of the tile at position row, col.
        """                 
        return self._grid[row][col];
poc_2048_gui.run_gui(TwentyFortyEight(4, 9))


你可能感兴趣的:(python)