Skip to content

Data Loss and Recursion Errors in Cell/Grid Deepcopy/Pickle #3221

@falloficarus22

Description

@falloficarus22

Description
The discrete_space system currently fails when attempting to copy or pickle models, particularly those with large grids. There are two distinct failure modes:

  • Data Loss: Standalone Cell objects explicitly set their neighbor connections to None during serialization in getstate. This makes it impossible to inspect or use connections on a copied cell.
  • Recursion Errors: For large grids (e.g., 100x100), the highly interconnected graph of cells triggers a RecursionError in Python's deepcopy and pickle modules because the default recursion limit is exceeded while traversing circular references.

Expected behavior

  • Performing a deepcopy on a Cell should preserve its connection metadata (keys and neighbor mapping).
  • Performing a deepcopy on a Grid (or any DiscreteSpace) should handle any size supported by Mesa without crashing, while ensuring that all circular references between cells are correctly reconstructed in the copy.

To Reproduce

import copy
from mesa.discrete_space import Cell, OrthogonalMooreGrid

# 1. Standalone Data Loss
c1 = Cell(coordinate=(0, 0))
c2 = Cell(coordinate=(0, 1))
c1.connect(c2)
c1_copy = copy.deepcopy(c1)
print(f"Neighbor in copy: {c1_copy.connections[(0, 1)]}") 
# Expected: (0, 1) or Cell object
# Actual: None

# 2. Recursion Error in Large Grids
grid = OrthogonalMooreGrid((100, 100))
# This triggers: RecursionError: maximum recursion depth exceeded
grid_copy = copy.deepcopy(grid) 

Additional context
The issue stems from the current Cell.__getstate__ implementation attempting to prevent recursion by simply nullifying objects. A more robust solution is to use a coordinate-based serialization strategy where Cell objects store neighbor coordinates during state extraction, and the parent DiscreteSpace container handles the relinking of these coordinates back into object references during state injection (setstate).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions