1

I am trying to implement a chess AI using a monte carlo tree search. This requires playing through 800 random games from each position to evaluate the value of each move. However, I am using a pygame sprite group to hold instances of the pieces, which I then loop through to find the possible moves for each piece in the position. When I take a piece I use the .kill() function as otherwise I will end up with my legal_moves() function returning moves from pieces that have been taken. However, when this is used in the search, it also kills the piece in the game, which I don't want it to do.

I have tried using the inbuilt copy function, but this is just a shallow copy. I tried copy.deepcopy(piece_list), but this gives an error message:

File "C:\Users\Sean\PycharmProjects\Chess\Monte_Carlo_Tree_Search.py", line 339, in run_mcts
exploration_game = copy.deepcopy(game)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py",  line 180, in deepcopy
y = _reconstruct(x, memo, *rv)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py",  line 280, in _reconstruct
state = deepcopy(state, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py",  line 150, in deepcopy
y = copier(x, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py",  line 240, in _deepcopy_dict
y[deepcopy(key, memo)] = deepcopy(value, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py",  line 180, in deepcopy
y = _reconstruct(x, memo, *rv)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 280, in _reconstruct
state = deepcopy(state, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 150, in deepcopy
y = copier(x, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 240, in _deepcopy_dict
y[deepcopy(key, memo)] = deepcopy(value, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 150, in deepcopy
y = copier(x, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 240, in _deepcopy_dict
y[deepcopy(key, memo)] = deepcopy(value, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 180, in deepcopy
y = _reconstruct(x, memo, *rv)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 280, in _reconstruct
state = deepcopy(state, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 150, in deepcopy
y = copier(x, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 240, in _deepcopy_dict
y[deepcopy(key, memo)] = deepcopy(value, memo)

File "C:\Users\Sean\AppData\Local\Programs\Python\Python37-32\lib\copy.py", line 169, in deepcopy
rv = reductor(4)

TypeError: can't pickle pygame.Surface objects

I've had a look around online, but none of the responses seem to give a way to do it, rather an alternate method.

import pygame

knight = pygame.sprite.Sprite()
piece_list = pygame.sprite.Group()
piece_list.add(knight)

piece_list_copy = piece_list.copy()

for piece in piece_list_copy:
    piece.kill()

print(piece_list)

I would want some method of changing this code such that it returns "Group(1 sprites)", as opposed to "Group(0 sprites)"

Arkleseisure
  • 416
  • 5
  • 19
  • Just realised that in the error example I had tried to deepcopy the entire game object... doing it separately I have had the same result. – Arkleseisure Aug 14 '19 at 18:54

1 Answers1

2

.copy() creates a new group, which contains the same sprites as the group, but the sprites are not (deep) copied.

You can use .remove() to remove a Sprite from a single pygame.sprite.Group:

for piece in piece_list_copy:
    piece_list.remove(piece)
Rabbid76
  • 202,892
  • 27
  • 131
  • 174