Repository: projectmesa/mesa
Pull request #1723 (2023-06-21 03:42:58)

breaking: Change coord_iter to return tuple[content, pos]
This PR recreates #1566.

codecov[bot]: ## [Codecov](https://app.codecov.io/gh/projectmesa/mesa/pull/1723?src=pr&el=h1&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa) Report
Patch coverage: **`100.00`**% and no project coverage change.
> Comparison is base [(`0db8f7c`)](https://app.codecov.io/gh/projectmesa/mesa/commit/0db8f7c7ad1277be64637ff7180722fad81df1d3?el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa) 79.93% compared to head [(`391489e`)](https://app.codecov.io/gh/projectmesa/mesa/pull/1723?src=pr&el=desc&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa) 79.93%.

<details><summary>Additional details and impacted files</summary>


```diff
@@           Coverage Diff           @@
##             main    #1723   +/-   ##
=======================================
  Coverage   79.93%   79.93%           
=======================================
  Files          18       18           
  Lines        1176     1176           
  Branches      220      220           
=======================================
  Hits          940      940           
  Misses        202      202           
  Partials       34       34           
```


| [Impacted Files](https://app.codecov.io/gh/projectmesa/mesa/pull/1723?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa) | Coverage Δ | |
|---|---|---|
| [mesa/space.py](https://app.codecov.io/gh/projectmesa/mesa/pull/1723?src=pr&el=tree&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa#diff-bWVzYS9zcGFjZS5weQ==) | `90.88% <100.00%> (ø)` | |


</details>

[:umbrella: View full report in Codecov by Sentry](https://app.codecov.io/gh/projectmesa/mesa/pull/1723?src=pr&el=continue&utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa).   
:loudspeaker: Do you have feedback about the report comment? [Let us know in this issue](https://about.codecov.io/codecov-pr-comment-feedback/?utm_medium=referral&utm_source=github&utm_content=comment&utm_campaign=pr+comments&utm_term=projectmesa).


Patch:
diff --git a/docs/tutorials/intro_tutorial.ipynb b/docs/tutorials/intro_tutorial.ipynb
index fe76ea03..22703cf4 100644
--- a/docs/tutorials/intro_tutorial.ipynb
+++ b/docs/tutorials/intro_tutorial.ipynb
@@ -788,7 +788,7 @@
    "cell_type": "markdown",
    "metadata": {},
    "source": [
-    "Now let's use matplotlib and numpy to visualize the number of agents residing in each cell. To do that, we create a numpy array of the same size as the grid, filled with zeros. Then we use the grid object's `coord_iter()` feature, which lets us loop over every cell in the grid, giving us each cell's coordinates and contents in turn."
+    "Now let's use matplotlib and numpy to visualize the number of agents residing in each cell. To do that, we create a numpy array of the same size as the grid, filled with zeros. Then we use the grid object's `coord_iter()` feature, which lets us loop over every cell in the grid, giving us each cell's positions and contents in turn."
    ]
   },
   {
@@ -805,8 +805,7 @@
     "import numpy as np\n",
     "\n",
     "agent_counts = np.zeros((model.grid.width, model.grid.height))\n",
-    "for cell in model.grid.coord_iter():\n",
-    "    cell_content, x, y = cell\n",
+    "for cell_content, (x, y) in model.grid.coord_iter():\n",
     "    agent_count = len(cell_content)\n",
     "    agent_counts[x][y] = agent_count\n",
     "# Plot using seaborn, with a size of 5x5\n",
diff --git a/mesa/space.py b/mesa/space.py
index 96e1a4da..9e9522e2 100644
--- a/mesa/space.py
+++ b/mesa/space.py
@@ -193,11 +193,11 @@ class _Grid:
         as if it is one list:"""
         return itertools.chain(*self._grid)
 
-    def coord_iter(self) -> Iterator[tuple[GridContent, int, int]]:
-        """An iterator that returns coordinates as well as cell contents."""
+    def coord_iter(self) -> Iterator[tuple[GridContent, Coordinate]]:
+        """An iterator that returns positions as well as cell contents."""
         for row in range(self.width):
             for col in range(self.height):
-                yield self._grid[row][col], row, col  # agent, x, y
+                yield self._grid[row][col], (row, col)  # agent, position
 
     def iter_neighborhood(
         self,


Test patch:
diff --git a/tests/test_grid.py b/tests/test_grid.py
index d263c90b..686d8e78 100644
--- a/tests/test_grid.py
+++ b/tests/test_grid.py
@@ -134,15 +134,13 @@ class TestSingleGrid(unittest.TestCase):
         # no agent in first space
         first = next(ci)
         assert first[0] is None
-        assert first[1] == 0
-        assert first[2] == 0
+        assert first[1] == (0, 0)
 
         # first agent in the second space
         second = next(ci)
         assert second[0].unique_id == 1
         assert second[0].pos == (0, 1)
-        assert second[1] == 0
-        assert second[2] == 1
+        assert second[1] == (0, 1)
 
     def test_agent_move(self):
         # get the agent at [0, 1]
@@ -480,8 +478,9 @@ class TestHexSingleGridTorus(TestSingleGrid):
 class TestIndexing:
     # Create a grid where the content of each coordinate is a tuple of its coordinates
     grid = SingleGrid(3, 5, True)
-    for _, x, y in grid.coord_iter():
-        grid._grid[x][y] = (x, y)
+    for _, pos in grid.coord_iter():
+        x, y = pos
+        grid._grid[x][y] = pos
 
     def test_int(self):
         assert self.grid[0][0] == (0, 0)
diff --git a/tests/test_visualization.py b/tests/test_visualization.py
index 2c3ebd4c..55e53cdb 100644
--- a/tests/test_visualization.py
+++ b/tests/test_visualization.py
@@ -40,7 +40,8 @@ class MockModel(Model):
         self.schedule = SimultaneousActivation(self)
         self.grid = MultiGrid(width, height, torus=True)
 
-        for _c, x, y in self.grid.coord_iter():
+        for _c, pos in self.grid.coord_iter():
+            x, y = pos
             a = MockAgent(x + y * 100, self, x * y * 3)
             self.grid.place_agent(a, (x, y))
             self.schedule.add(a)