I am a novice functional programmer. So if you find any areas of suggested improvement on my FP skills, do add a comment below.
Below is a sample Tic Tac Toe written using Functional Programming constructs (or at least whatever I understood about them).
Right now, I’ve implemented only a simple player who basically marks off a cell randomly. It should be possible to define more intelligent players similarly. Hopefully all the comments in the code should be sufficiently self explanatory.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 | import random import functools import itertools import copy def row_gen(board): """ Generator which returns tuples of tuples. The outer tuple represents a row. The inner tuple represents each cell with its coordinates and data """ return ( tuple((row,col,board[row][col]) for col in range(3)) for row in range(3)) def col_gen(board): """ Generator which returns tuples of tuples. The outer tuple represents a column. The inner tuple represents each cell with its coordinates and data """ return ( tuple((row,col,board[row][col]) for row in range(3)) for col in range(3)) def dia_gen(board): """ Generator which returns two tuples of tuples. The outer tuple represents a diagonal. The inner tuple represents each cell with its coordinates and data """ return ( tuple((i,i,board[i][i]) for i in range(3)), tuple((i,2-i,board[i][2-i]) for i in range(3))) def empty(board): """ Gets a list of all empty cells on the board """ return ( (row,col) for row in range(3) for col in range(3) if board[row][col] == None) def is_empty(board): """ checks if any cell on the board is still empty """ for row in range(3) : for col in range(3) : if board[row][col] is None : return False return True def random_player(chr,board): """Represents a player who randomly marks his next move """ empty_cells = list(empty(board)) play = empty_cells[random.randint(0,len(empty_cells)-1)] board = copy.copy(board) board[play[0]][play[1]] = chr return board def show(board): """ Shows the current representation of the board """ print '+-+-+-+' for row in range(3) : print '|%s|' % '|'.join( board[row][col]if board[row][col] is not None else ' ' for col in range(3)) print '+-+-+-+' if __name__ == '__main__' : # Initialise the board with all values set to None board = list(list(None for i in range(3)) for j in range(3)) show(board) # Initialise the two players. Each is given a separate char player1 = functools.partial(random_player,'X') player2 = functools.partial(random_player,'O') # Setup an iterator to continuously cycle through both players players = itertools.cycle((player1,player2)) # Play game over = False while not over and not is_empty(board) : # Ask the next player to make his move board = players.next()(board) show(board) # Note a cell bag set is all rows, # all cols and all diagonals for cell_bag_set in ( row_gen(board), col_gen(board), dia_gen(board)) : # Note a cell_bag can be a row, column or a dia for cell_bag in cell_bag_set : vals = set(val[2] for val in cell_bag) if len(vals) == 1 and \ vals.__iter__().next() is not None : over = True print 'Over' break |
Tags: functional programming, games, tic tac toe

