Mesa 3.1.1__tar.gz → 3.1.3__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of Mesa might be problematic. Click here for more details.

Files changed (190) hide show
  1. {mesa-3.1.1 → mesa-3.1.3}/.pre-commit-config.yaml +2 -2
  2. {mesa-3.1.1 → mesa-3.1.3}/CONTRIBUTING.md +2 -0
  3. {mesa-3.1.1 → mesa-3.1.3}/HISTORY.md +74 -0
  4. {mesa-3.1.1 → mesa-3.1.3}/PKG-INFO +5 -2
  5. {mesa-3.1.1 → mesa-3.1.3}/benchmarks/configurations.py +9 -4
  6. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/experimental.md +12 -0
  7. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/intro_tutorial.ipynb +22 -22
  8. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/visualization_tutorial.ipynb +7 -7
  9. {mesa-3.1.1 → mesa-3.1.3}/mesa/__init__.py +1 -1
  10. mesa-3.1.3/mesa/examples/advanced/pd_grid/analysis.ipynb +183 -0
  11. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/wolf_sheep/agents.py +33 -1
  12. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boid_flockers/agents.py +26 -38
  13. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boid_flockers/app.py +6 -1
  14. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boid_flockers/model.py +30 -37
  15. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/analysis.ipynb +42 -36
  16. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/app.py +1 -1
  17. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/model.py +3 -3
  18. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/__init__.py +2 -2
  19. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/voronoi.py +1 -4
  20. mesa-3.1.3/mesa/experimental/continuous_space/__init__.py +8 -0
  21. mesa-3.1.3/mesa/experimental/continuous_space/continuous_space.py +273 -0
  22. mesa-3.1.3/mesa/experimental/continuous_space/continuous_space_agents.py +101 -0
  23. {mesa-3.1.1 → mesa-3.1.3}/mesa/model.py +1 -1
  24. {mesa-3.1.1 → mesa-3.1.3}/mesa/space.py +7 -0
  25. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/mpl_space_drawing.py +22 -13
  26. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/solara_viz.py +30 -7
  27. {mesa-3.1.1 → mesa-3.1.3}/pyproject.toml +1 -0
  28. mesa-3.1.3/tests/test_continuous_space.py +432 -0
  29. {mesa-3.1.1 → mesa-3.1.3}/tests/test_model.py +12 -0
  30. mesa-3.1.1/mesa/examples/advanced/pd_grid/analysis.ipynb +0 -228
  31. {mesa-3.1.1 → mesa-3.1.3}/.codespellignore +0 -0
  32. {mesa-3.1.1 → mesa-3.1.3}/.coveragerc +0 -0
  33. {mesa-3.1.1 → mesa-3.1.3}/.github/ISSUE_TEMPLATE/bug-report.md +0 -0
  34. {mesa-3.1.1 → mesa-3.1.3}/.github/ISSUE_TEMPLATE/config.yml +0 -0
  35. {mesa-3.1.1 → mesa-3.1.3}/.github/ISSUE_TEMPLATE/feature-request.md +0 -0
  36. {mesa-3.1.1 → mesa-3.1.3}/.github/PULL_REQUEST_TEMPLATE/bug.md +0 -0
  37. {mesa-3.1.1 → mesa-3.1.3}/.github/PULL_REQUEST_TEMPLATE/feature.md +0 -0
  38. {mesa-3.1.1 → mesa-3.1.3}/.github/dependabot.yml +0 -0
  39. {mesa-3.1.1 → mesa-3.1.3}/.github/pull_request_template.md +0 -0
  40. {mesa-3.1.1 → mesa-3.1.3}/.github/release.yml +0 -0
  41. {mesa-3.1.1 → mesa-3.1.3}/.github/workflows/benchmarks.yml +0 -0
  42. {mesa-3.1.1 → mesa-3.1.3}/.github/workflows/build_lint.yml +0 -0
  43. {mesa-3.1.1 → mesa-3.1.3}/.github/workflows/release.yml +0 -0
  44. {mesa-3.1.1 → mesa-3.1.3}/.gitignore +0 -0
  45. {mesa-3.1.1 → mesa-3.1.3}/.readthedocs.yml +0 -0
  46. {mesa-3.1.1 → mesa-3.1.3}/CITATION.bib +0 -0
  47. {mesa-3.1.1 → mesa-3.1.3}/CODE_OF_CONDUCT.md +0 -0
  48. {mesa-3.1.1 → mesa-3.1.3}/Dockerfile +0 -0
  49. {mesa-3.1.1 → mesa-3.1.3}/LICENSE +0 -0
  50. {mesa-3.1.1 → mesa-3.1.3}/NOTICE +0 -0
  51. {mesa-3.1.1 → mesa-3.1.3}/README.md +0 -0
  52. {mesa-3.1.1 → mesa-3.1.3}/benchmarks/compare_timings.py +0 -0
  53. {mesa-3.1.1 → mesa-3.1.3}/benchmarks/global_benchmark.py +0 -0
  54. {mesa-3.1.1 → mesa-3.1.3}/binder/environment.yml +0 -0
  55. {mesa-3.1.1 → mesa-3.1.3}/codecov.yaml +0 -0
  56. {mesa-3.1.1 → mesa-3.1.3}/docker-compose.yml +0 -0
  57. {mesa-3.1.1 → mesa-3.1.3}/docs/Makefile +0 -0
  58. {mesa-3.1.1 → mesa-3.1.3}/docs/README.md +0 -0
  59. {mesa-3.1.1 → mesa-3.1.3}/docs/_static/switcher.json +0 -0
  60. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/agent.md +0 -0
  61. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/api_main.md +0 -0
  62. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/batchrunner.md +0 -0
  63. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/datacollection.md +0 -0
  64. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/mesa_logging.md +0 -0
  65. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/model.md +0 -0
  66. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/space.md +0 -0
  67. {mesa-3.1.1 → mesa-3.1.3}/docs/apis/visualization.md +0 -0
  68. {mesa-3.1.1 → mesa-3.1.3}/docs/best-practices.md +0 -0
  69. {mesa-3.1.1 → mesa-3.1.3}/docs/conf.py +0 -0
  70. {mesa-3.1.1 → mesa-3.1.3}/docs/example_template.txt +0 -0
  71. {mesa-3.1.1 → mesa-3.1.3}/docs/examples_overview_template.txt +0 -0
  72. {mesa-3.1.1 → mesa-3.1.3}/docs/getting_started.md +0 -0
  73. {mesa-3.1.1 → mesa-3.1.3}/docs/images/mesa_logo.ico +0 -0
  74. {mesa-3.1.1 → mesa-3.1.3}/docs/images/mesa_logo.png +0 -0
  75. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/br_ginis.png +0 -0
  76. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/dc_endwealth.png +0 -0
  77. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/dc_gini.png +0 -0
  78. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/dc_oneagent.png +0 -0
  79. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/first_hist.png +0 -0
  80. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/multirun_hist.png +0 -0
  81. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/numpy_grid.png +0 -0
  82. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/viz_chart.png +0 -0
  83. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/viz_empty.png +0 -0
  84. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/viz_greycircles.png +0 -0
  85. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/viz_histogram.png +0 -0
  86. {mesa-3.1.1 → mesa-3.1.3}/docs/images/tutorial/viz_redcircles.png +0 -0
  87. {mesa-3.1.1 → mesa-3.1.3}/docs/images/wolf_sheep.png +0 -0
  88. {mesa-3.1.1 → mesa-3.1.3}/docs/index.md +0 -0
  89. {mesa-3.1.1 → mesa-3.1.3}/docs/make.bat +0 -0
  90. {mesa-3.1.1 → mesa-3.1.3}/docs/mesa.md +0 -0
  91. {mesa-3.1.1 → mesa-3.1.3}/docs/migration_guide.md +0 -0
  92. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/MoneyModel.py +0 -0
  93. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_chart.png +0 -0
  94. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_empty.png +0 -0
  95. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_greycircles.png +0 -0
  96. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_histogram.png +0 -0
  97. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_redcircles.png +0 -0
  98. {mesa-3.1.1 → mesa-3.1.3}/docs/tutorials/files/viz_slider.png +0 -0
  99. {mesa-3.1.1 → mesa-3.1.3}/maintenance/fetch_unlabeled_prs.py +0 -0
  100. {mesa-3.1.1 → mesa-3.1.3}/mesa/agent.py +0 -0
  101. {mesa-3.1.1 → mesa-3.1.3}/mesa/batchrunner.py +0 -0
  102. {mesa-3.1.1 → mesa-3.1.3}/mesa/datacollection.py +0 -0
  103. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/README.md +0 -0
  104. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/__init__.py +0 -0
  105. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/__init__.py +0 -0
  106. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/Epstein Civil Violence.ipynb +0 -0
  107. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/Readme.md +0 -0
  108. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/__init__.py +0 -0
  109. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/agents.py +0 -0
  110. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/app.py +0 -0
  111. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/epstein_civil_violence/model.py +0 -0
  112. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/pd_grid/Readme.md +0 -0
  113. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/pd_grid/__init__.py +0 -0
  114. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/pd_grid/agents.py +0 -0
  115. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/pd_grid/app.py +0 -0
  116. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/pd_grid/model.py +0 -0
  117. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/Readme.md +0 -0
  118. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/__init__.py +0 -0
  119. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/agents.py +0 -0
  120. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/app.py +0 -0
  121. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/model.py +0 -0
  122. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/sugar-map.txt +0 -0
  123. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/sugarscape_g1mt/tests.py +0 -0
  124. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/wolf_sheep/Readme.md +0 -0
  125. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/wolf_sheep/__init__.py +0 -0
  126. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/wolf_sheep/app.py +0 -0
  127. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/advanced/wolf_sheep/model.py +0 -0
  128. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/__init__.py +0 -0
  129. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boid_flockers/Readme.md +0 -0
  130. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boid_flockers/__init__.py +0 -0
  131. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/Readme.md +0 -0
  132. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/__init__.py +0 -0
  133. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/agents.py +0 -0
  134. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/app.py +0 -0
  135. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/model.py +0 -0
  136. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/boltzmann_wealth_model/st_app.py +0 -0
  137. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/Readme.md +0 -0
  138. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/__init__.py +0 -0
  139. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/agents.py +0 -0
  140. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/app.py +0 -0
  141. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/model.py +0 -0
  142. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/conways_game_of_life/st_app.py +0 -0
  143. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/Readme.md +0 -0
  144. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/__init__.py +0 -0
  145. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/schelling/agents.py +0 -0
  146. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/virus_on_network/Readme.md +0 -0
  147. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/virus_on_network/__init__.py +0 -0
  148. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/virus_on_network/agents.py +0 -0
  149. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/virus_on_network/app.py +0 -0
  150. {mesa-3.1.1 → mesa-3.1.3}/mesa/examples/basic/virus_on_network/model.py +0 -0
  151. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/__init__.py +0 -0
  152. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/cell.py +0 -0
  153. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/cell_agent.py +0 -0
  154. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/cell_collection.py +0 -0
  155. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/discrete_space.py +0 -0
  156. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/grid.py +0 -0
  157. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/network.py +0 -0
  158. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/cell_space/property_layer.py +0 -0
  159. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/devs/__init__.py +0 -0
  160. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/devs/eventlist.py +0 -0
  161. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/devs/simulator.py +0 -0
  162. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/mesa_signals/__init__.py +0 -0
  163. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/mesa_signals/mesa_signal.py +0 -0
  164. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/mesa_signals/observable_collections.py +0 -0
  165. {mesa-3.1.1 → mesa-3.1.3}/mesa/experimental/mesa_signals/signals_util.py +0 -0
  166. {mesa-3.1.1 → mesa-3.1.3}/mesa/mesa_logging.py +0 -0
  167. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/__init__.py +0 -0
  168. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/components/__init__.py +0 -0
  169. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/components/altair_components.py +0 -0
  170. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/components/matplotlib_components.py +0 -0
  171. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/user_param.py +0 -0
  172. {mesa-3.1.1 → mesa-3.1.3}/mesa/visualization/utils.py +0 -0
  173. {mesa-3.1.1 → mesa-3.1.3}/mypy.ini +0 -0
  174. {mesa-3.1.1 → mesa-3.1.3}/tests/__init__.py +0 -0
  175. {mesa-3.1.1 → mesa-3.1.3}/tests/read_requirements.py +0 -0
  176. {mesa-3.1.1 → mesa-3.1.3}/tests/test_agent.py +0 -0
  177. {mesa-3.1.1 → mesa-3.1.3}/tests/test_batch_run.py +0 -0
  178. {mesa-3.1.1 → mesa-3.1.3}/tests/test_cell_space.py +0 -0
  179. {mesa-3.1.1 → mesa-3.1.3}/tests/test_components_matplotlib.py +0 -0
  180. {mesa-3.1.1 → mesa-3.1.3}/tests/test_datacollector.py +0 -0
  181. {mesa-3.1.1 → mesa-3.1.3}/tests/test_devs.py +0 -0
  182. {mesa-3.1.1 → mesa-3.1.3}/tests/test_end_to_end_viz.sh +0 -0
  183. {mesa-3.1.1 → mesa-3.1.3}/tests/test_examples.py +0 -0
  184. {mesa-3.1.1 → mesa-3.1.3}/tests/test_grid.py +0 -0
  185. {mesa-3.1.1 → mesa-3.1.3}/tests/test_import_namespace.py +0 -0
  186. {mesa-3.1.1 → mesa-3.1.3}/tests/test_lifespan.py +0 -0
  187. {mesa-3.1.1 → mesa-3.1.3}/tests/test_mesa_logging.py +0 -0
  188. {mesa-3.1.1 → mesa-3.1.3}/tests/test_mesa_signals.py +0 -0
  189. {mesa-3.1.1 → mesa-3.1.3}/tests/test_solara_viz.py +0 -0
  190. {mesa-3.1.1 → mesa-3.1.3}/tests/test_space.py +0 -0
@@ -4,7 +4,7 @@ ci:
4
4
  repos:
5
5
  - repo: https://github.com/astral-sh/ruff-pre-commit
6
6
  # Ruff version.
7
- rev: v0.8.1
7
+ rev: v0.8.6
8
8
  hooks:
9
9
  # Run the linter.
10
10
  - id: ruff
@@ -14,7 +14,7 @@ repos:
14
14
  - id: ruff-format
15
15
  types_or: [ python, pyi, jupyter ]
16
16
  - repo: https://github.com/asottile/pyupgrade
17
- rev: v3.19.0
17
+ rev: v3.19.1
18
18
  hooks:
19
19
  - id: pyupgrade
20
20
  args: [--py311-plus]
@@ -137,6 +137,8 @@ To create a new release, follow these steps:
137
137
  9. The [`release.yml`](https://github.com/projectmesa/mesa/blob/main/.github/workflows/release.yml) CI workflow should automatically create and upload the package to PyPI. Verify this on [PyPI.org](https://pypi.org/project/mesa/).
138
138
  10. Finally, after release, open a new PR to update the version number in [`mesa/__init__.py`](https://github.com/projectmesa/mesa/blob/main/mesa/__init__.py) for the next release (e.g., `"3.1.0.dev"`).
139
139
 
140
+ A recorded video of this process is [available here](https://youtu.be/JE44jkegmns).
141
+
140
142
  ## Special Thanks
141
143
 
142
144
  A special thanks to the following projects who offered inspiration for this contributing file.
@@ -1,6 +1,80 @@
1
1
  ---
2
2
  title: Release History
3
3
  ---
4
+ # 3.1.3 (2025-01-11)
5
+ ## Highlights
6
+ Mesa 3.1.3 introduces a major experimental reimplementation of Mesa's continuous space, providing an intuitive agent-centric API and significant performance improvements. The new implementation supports n-dimensional spaces and offers streamlined methods for agent movement and neighbor calculations.
7
+
8
+ ### New Continuous Space Features
9
+ - Agent-centric movement API similar to cell spaces
10
+ - Efficient neighbor calculations and position updates
11
+ - Support for n-dimensional spaces
12
+ - Improved memory management with dynamic array resizing
13
+
14
+ Here's a quick look at the new API:
15
+
16
+ ```python
17
+ # Create a 2D continuous space
18
+ space = ContinuousSpace(
19
+ dimensions=[[0, 1], [0, 1]],
20
+ torus=True,
21
+ random=model.random
22
+ )
23
+
24
+ # Create and position an agent
25
+ agent = ContinuousSpaceAgent(space, model)
26
+ agent.position = [0.5, 0.5]
27
+
28
+ # Move agent using vector arithmetic
29
+ agent.position += [0.1, 0.1]
30
+
31
+ # Get neighbors within radius
32
+ neighbors, distances = agent.get_neighbors_in_radius(radius=0.2)
33
+
34
+ # Find k nearest neighbors
35
+ nearest, distances = agent.get_nearest_neighbors(k=5)
36
+ ```
37
+
38
+ The new implementation particularly benefits models requiring frequent position updates and neighbor queries, such as flocking simulations or particle systems. See [#2584](https://github.com/projectmesa/mesa/pull/2584) for more details. We would love to get feedback on the new Continuous Space in [#2611](https://github.com/projectmesa/mesa/discussions/2611).
39
+
40
+ Other improvements in this release include consistent visualization behavior across space types with the reimplementation of `draw_voronoi` [#2608](https://github.com/projectmesa/mesa/pull/2608), and a new render interval slider for controlling visualization update frequency in SolaraViz, which helps improve performance when working with complex visualizations [#2596](https://github.com/projectmesa/mesa/pull/2596). We've also fixed a bug affecting random number generation determinism when using `Model(seed=something)`, ensuring both `model.random` and `model.rng` now behave consistently when seeded with the same initial value [#2598](https://github.com/projectmesa/mesa/pull/2598).
41
+
42
+ ## What's Changed
43
+ ### 🧪 Experimental features
44
+ * Reimplementation of Continuous Space by @quaquel in https://github.com/projectmesa/mesa/pull/2584
45
+ ### 🛠 Enhancements made
46
+ * reimplementation of draw_voroinoi by @quaquel in https://github.com/projectmesa/mesa/pull/2608
47
+ * Add render interval slider to control visualization update frequency by @HMNS19 in https://github.com/projectmesa/mesa/pull/2596
48
+ ### 🐛 Bugs fixed
49
+ * Bugfix for non deterministic rng behavior by @quaquel in https://github.com/projectmesa/mesa/pull/2598
50
+ ### 🔍 Examples updated
51
+ * Clarify ContinuousSpace.get_neighbors behavior with multiple agents at same position by @quaquel in https://github.com/projectmesa/mesa/pull/2599
52
+
53
+ ## New Contributors
54
+ * @HMNS19 made their first contribution in https://github.com/projectmesa/mesa/pull/2596
55
+
56
+ **Full Changelog**: https://github.com/projectmesa/mesa/compare/v3.1.2...v3.1.3
57
+
58
+ # 3.1.2 (2025-01-04)
59
+ ## Highlights
60
+ Mesa v3.1.2 is a patch release containing updates to our wolf-sheep, shelling and prisoner's dilemma example models and improving documentation in the tutorials and visualisation docstring. No functional changes to the core library were made.
61
+
62
+ ## What's Changed
63
+ ### 🔍 Examples updated
64
+ * examples/wolf_sheep: Don't allow dumb moves by @EwoutH in https://github.com/projectmesa/mesa/pull/2503
65
+ * Added homophily ratio in basic schelling example by @vbv-shm in https://github.com/projectmesa/mesa/pull/2520
66
+ * examples: Update pd_grid analysis.ipynb to use new spaces by @quaquel in https://github.com/projectmesa/mesa/pull/2553
67
+ ### 📜 Documentation improvements
68
+ * Corrected a few errors in Intro tutorial by @sanika-n in https://github.com/projectmesa/mesa/pull/2583
69
+ * Small draw_space docstring fix by @quaquel in https://github.com/projectmesa/mesa/pull/2554
70
+ * fix: model name in visualization tutorial by @Sahil-Chhoker in https://github.com/projectmesa/mesa/pull/2591
71
+
72
+ ## New Contributors
73
+ * @vbv-shm made their first contribution in https://github.com/projectmesa/mesa/pull/2520
74
+ * @sanika-n made their first contribution in https://github.com/projectmesa/mesa/pull/2583
75
+
76
+ **Full Changelog**: https://github.com/projectmesa/mesa/compare/v3.1.1...v3.1.2
77
+
4
78
  # 3.1.1 (2024-12-14)
5
79
  ## Highlights
6
80
  Mesa 3.1.1 is a maintenance release that includes visualization improvements and documentation updates. The key enhancement is the addition of an interactive play interval control to the visualization interface, allowing users to dynamically adjust simulation speed between 1ms and 500ms through a slider in the Controls panel.
@@ -1,11 +1,13 @@
1
- Metadata-Version: 2.3
1
+ Metadata-Version: 2.4
2
2
  Name: Mesa
3
- Version: 3.1.1
3
+ Version: 3.1.3
4
4
  Summary: Agent-based modeling (ABM) in Python
5
5
  Project-URL: homepage, https://github.com/projectmesa/mesa
6
6
  Project-URL: repository, https://github.com/projectmesa/mesa
7
7
  Author-email: Project Mesa Team <projectmesa@googlegroups.com>
8
8
  License: Apache 2.0
9
+ License-File: LICENSE
10
+ License-File: NOTICE
9
11
  Keywords: ABM,agent,based,model,modeling,multi-agent,simulation
10
12
  Classifier: Development Status :: 3 - Alpha
11
13
  Classifier: Intended Audience :: Science/Research
@@ -22,6 +24,7 @@ Classifier: Topic :: Scientific/Engineering :: Artificial Life
22
24
  Requires-Python: >=3.11
23
25
  Requires-Dist: numpy
24
26
  Requires-Dist: pandas
27
+ Requires-Dist: scipy
25
28
  Requires-Dist: tqdm
26
29
  Provides-Extra: all
27
30
  Requires-Dist: ipython; extra == 'all'
@@ -35,7 +35,7 @@ configurations = {
35
35
  "parameters": {
36
36
  "height": 40,
37
37
  "width": 40,
38
- "homophily": 3,
38
+ "homophily": 0.4,
39
39
  "radius": 1,
40
40
  "density": 0.625,
41
41
  },
@@ -47,7 +47,7 @@ configurations = {
47
47
  "parameters": {
48
48
  "height": 100,
49
49
  "width": 100,
50
- "homophily": 8,
50
+ "homophily": 1,
51
51
  "radius": 2,
52
52
  "density": 0.8,
53
53
  },
@@ -90,14 +90,19 @@ configurations = {
90
90
  "seeds": 25,
91
91
  "replications": 3,
92
92
  "steps": 20,
93
- "parameters": {"population": 200, "width": 100, "height": 100, "vision": 5},
93
+ "parameters": {
94
+ "population_size": 200,
95
+ "width": 100,
96
+ "height": 100,
97
+ "vision": 5,
98
+ },
94
99
  },
95
100
  "large": {
96
101
  "seeds": 10,
97
102
  "replications": 3,
98
103
  "steps": 10,
99
104
  "parameters": {
100
- "population": 400,
105
+ "population_size": 400,
101
106
  "width": 150,
102
107
  "height": 150,
103
108
  "vision": 15,
@@ -54,3 +54,15 @@ This namespace contains experimental features. These are under development, and
54
54
  .. automodule:: experimental.devs.simulator
55
55
  :members:
56
56
  ```
57
+
58
+ ## Continuous Space
59
+
60
+ ```{eval-rst}
61
+ .. automodule:: experimental.continuous_space.continuous_space
62
+ :members:
63
+ ```
64
+
65
+ ```{eval-rst}
66
+ .. automodule:: experimental.continuous_space.continuous_space_agents
67
+ :members:
68
+ ```
@@ -14,7 +14,7 @@
14
14
  "metadata": {},
15
15
  "source": [
16
16
  "**Important:** \n",
17
- "- If you are just exploring Mesa and want the fastest way to execute the code we recommend executing this tutorial online in a Colab notebook. [![Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/projectmesa/mesa/blob/main/docs/tutorials/intro_tutorial.ipynb) or if you do not have a Google account you can use [![Binder](https://mybinder.org/badge_logo.svg)](https://mybinder.org/v2/gh/projectmesa/mesa/main?labpath=docs%2Ftutorials%2Fintro_tutorial.ipynb) (Thas can take 30 seconds to 5 minutes to load)\n",
17
+ "- If you are just exploring Mesa and want the fastest way to execute the code we recommend executing this tutorial online in a Colab notebook. [![Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/projectmesa/mesa/blob/main/docs/tutorials/intro_tutorial.ipynb) or if you do not have a Google account you can use [![Binder](https://mybinder.org/badge_logo.svg)](https://mybinder.org/v2/gh/projectmesa/mesa/main?labpath=docs%2Ftutorials%2Fintro_tutorial.ipynb) (This can take 30 seconds to 5 minutes to load)\n",
18
18
  "- If you have installed mesa and are running locally, please ensure that your Mesa version is greater than or equal to 3.0.0b1.\n",
19
19
  "\n",
20
20
  "## Tutorial Description\n",
@@ -68,7 +68,7 @@
68
68
  "\n",
69
69
  "Even as a starter-level model it yields results that are both interesting and unexpected. \n",
70
70
  "\n",
71
- "Due to its simplicity and intrquiging results, we found ti to be a greater starter model. "
71
+ "Due to its simplicity and intriguing results, we found it to be the best starter model. "
72
72
  ]
73
73
  },
74
74
  {
@@ -104,7 +104,7 @@
104
104
  "```\n",
105
105
  "\n",
106
106
  "\n",
107
- "**If running in Google Colab run the below cell to install Mesa.** (This will also work in a locally installed version of Jupyter.)"
107
+ "**If running in Google Colab run the below cell to install Mesa.** (This will also work in a locally installed version of Jupyter)."
108
108
  ]
109
109
  },
110
110
  {
@@ -226,7 +226,7 @@
226
226
  "\n",
227
227
  "**Background:** The model can be visualized as a list containing all the agents. The model creates, holds and manages all the agent objects, specifically in a dictionary. The model activates agents in discrete time steps.\n",
228
228
  "\n",
229
- "**Model-specific information:** When a model is created the number of agents within the model is specified. The model then creates the agents and places them in an set of agents. \n",
229
+ "**Model-specific information:** When a model is created the number of agents within the model is specified. The model then creates the agents and places them in a set of agents. \n",
230
230
  "\n",
231
231
  "**Code implementation:** This is done by creating a new class (or object) that extends `mesa.Model` and calls `super().__init__()`, creating a subclass of the `Model` class from mesa. The new class is named `MoneyModel`. The technical details about the model object can be found in [model module](https://github.com/projectmesa/mesa/blob/main/mesa/model.py) and the AgentSet in the [agent module](https://github.com/projectmesa/mesa/blob/d7a3834c99a3be809abe2edc8b83610f3d4438ba/mesa/agent.py#L86). A critical point is that you can use the `seed` kwarg (keyword argument) to set a seed which controls the random number generator of the model class allowing for the reproducibility of results. \n",
232
232
  "\n",
@@ -256,11 +256,11 @@
256
256
  "source": [
257
257
  "### Making the Agents `do`\n",
258
258
  "\n",
259
- "With the basics of the Agent class and Model class created we can no activate the agents to `do` things\n",
259
+ "With the basics of the Agent class and Model class created we can now activate the agents to `do` things\n",
260
260
  "\n",
261
- "**Background:** Mesa's `do` function calls agent functions the grow your ABM. A step is the smallest unit of time in the model, and is often referred to as a tick. The `do` function and Python functionality can be configured to activate agents in different orders. This can be important as the order in which agents are activated can impact the results of the model [Comer2014]. At each step of the model, one or more of the agents -- usually all of them -- are activated and take their own step, changing internally and/or interacting with one another or the environment.\n",
261
+ "**Background:** Mesa's `do` function calls agent functions to grow your ABM. A step is the smallest unit of time in the model, and is often referred to as a tick. The `do` function and Python functionality can be configured to activate agents in different orders. This can be important as the order in which agents are activated can impact the results of the model [Comer2014]. At each step of the model, one or more of the agents -- usually all of them -- are activated and take their own step, changing internally and/or interacting with one another or the environment.\n",
262
262
  "\n",
263
- "**Model-specific information:** For this section we will randomly reorder the Agent activation order using `mesa.Agent.shuffle_do` and have the agents `step` function print the agent unique id they are assigned during the agent creation process. \n",
263
+ "**Model-specific information:** For this section we will randomly reorder the Agent activation order using `mesa.Agent.shuffle_do` and have the agents `step` function print the agent's unique id that they were assigned during the agent creation process. \n",
264
264
  "\n",
265
265
  "**Code implementation:** Using standard ABM convention we add a `step` function to the `MoneyModel` class which calls the `mesa.Agent.shuffle_do` function. We then pass into `shuffle_do` the parameter \"step\". This tells mesa to look for and execute the `step` function in our MoneyAgent class. "
266
266
  ]
@@ -569,7 +569,7 @@
569
569
  "cell_type": "markdown",
570
570
  "metadata": {},
571
571
  "source": [
572
- "This runs 100 instantiations of the model, and runs each for 10 steps. (notice that we set the histogram bins to be integers, since agents can only have whole numbers of wealth). This distribution looks a lot smoother. By running the model 100 times, we smooth out some of the 'noise' of randomness, and get to the model's overall expected behavior.\n",
572
+ "This runs 100 instantiations of the model, and runs each for 30 steps. (notice that we set the histogram bins to be integers, since agents can only have whole numbers of wealth). This distribution looks a lot smoother. By running the model 100 times, we smooth out some of the 'noise' of randomness, and get to the model's overall expected behavior.\n",
573
573
  "\n",
574
574
  "This outcome might be surprising. Despite the fact that all agents, on average, give and receive one unit of money every step, the model converges to a state where most agents have a small amount of money and a small number have a lot of money."
575
575
  ]
@@ -580,7 +580,7 @@
580
580
  "source": [
581
581
  "## Adding space\n",
582
582
  "\n",
583
- "**Background:** Many ABMs have a spatial element, with agents moving around and interacting with nearby neighbors. Mesa has several types of [spaces](https://mesa.readthedocs.io/latest/apis/space.html) from different types of grids to networks to an in development [cell_space](https://mesa.readthedocs.io/latest/apis/experimental.html#module-experimental.cell_space.__init__). Mesa grids are divided into cells, and agents can only be on a particular cell, like pieces on a chess board. Continuous space, in contrast, allows agents to have any arbitrary position. (Think of grids vs continuous space like the difference between integers and decimals.)\n",
583
+ "**Background:** Many ABMs have a spatial element, with agents moving around and interacting with nearby neighbors. Mesa has several types of [spaces](https://mesa.readthedocs.io/latest/apis/space.html) from different types of grids to networks to an in development [cell_space](https://mesa.readthedocs.io/latest/apis/experimental.html#module-experimental.cell_space.__init__). Mesa grids are divided into cells, and agents can only be on a particular cell, like pieces on a chess board. Continuous space, in contrast, allows agents to have any arbitrary position. (Think of grids vs continuous space like the difference between integers and decimals).\n",
584
584
  "\n",
585
585
  "Both grids and continuous spaces are frequently [toroidal](https://en.wikipedia.org/wiki/Toroidal_graph), meaning that the edges wrap around, with cells on the right edge connected to those on the left edge, and the top to the bottom. This prevents some cells having fewer neighbors than others, or agents being able to go off the edge of the environment. You can envision a torous by thinking of donut.\n",
586
586
  "\n",
@@ -800,14 +800,14 @@
800
800
  "Since one of the main goals of agent-based modeling is generating data for analysis, Mesa provides a class which can handle data collection and storage for us and make it easier to analyze.\n",
801
801
  "\n",
802
802
  "The data collector stores three categories of data: \n",
803
- " - Model-level variables : Model-level collection functions take a model object as an input. Such as a function that computes a dynamic of the whole model (in this case we will compute a measure of wealth inequality based on all agents wealth)\n",
803
+ " - Model-level variables : Model-level collection functions take a model object as an input. Such as a function that computes a dynamic of the whole model (in this case we will compute a measure of wealth inequality based on all agent's wealth)\n",
804
804
  " - Agent-level variables: Agent-level collection functions take an agent object as an input and is typically the state of an agent attributes, in this case wealth.\n",
805
805
  " - Tables (which are a catch-all for everything else). \n",
806
806
  "\n",
807
807
  "**Model-specific information:** We will collect two variables to show Mesa capabilities. At the model level, let's measure the model's [Gini Coefficient](https://en.wikipedia.org/wiki/Gini_coefficient), a measure of wealth inequality. At the agent level, we want to collect every agent's wealth at every step. \n",
808
808
  "\n",
809
809
  "**Code implementation:**\n",
810
- "Let's add a DataCollector to the model with [`mesa.DataCollector`](https://github.com/projectmesa/mesa/blob/main/mesa/datacollection.py), and collect the agents wealth and the gini coefficient at each time step. "
810
+ "Let's add a DataCollector to the model with [`mesa.DataCollector`](https://github.com/projectmesa/mesa/blob/main/mesa/datacollection.py), and collect the agent's wealth and the gini coefficient at each time step. "
811
811
  ]
812
812
  },
813
813
  {
@@ -882,9 +882,9 @@
882
882
  "source": [
883
883
  "At every step of the model, the datacollector will collect and store the model-level current Gini coefficient, as well as each agent's wealth, associating each with the current step.\n",
884
884
  "\n",
885
- "We run the model just as we did above. now is when an interactive session, especially via a notebook, comes in handy: the DataCollector can export the data its collected as a pandas* DataFrame, for easy interactive analysis. \n",
885
+ "We run the model just as we did above. Now is when an interactive session, especially via a notebook, comes in handy: the DataCollector can export the data it has collected as a pandas* DataFrame, for easy and interactive analysis. \n",
886
886
  "\n",
887
- "*If you are new to Python, please be aware that pandas is already installed as a dependency of Mesa and that [pandas](https://pandas.pydata.org/docs/) is a \"fast, powerful, flexible and easy to use open source data analysis and manipulation tool\". pandas is great resource to help analyze the data collected in your models."
887
+ "*If you are new to Python, please be aware that pandas is already installed as a dependency of Mesa and that [pandas](https://pandas.pydata.org/docs/) is a \"fast, powerful, flexible and easy to use open source data analysis and manipulation tool\". Pandas is a great resource to help analyze the data collected in your models."
888
888
  ]
889
889
  },
890
890
  {
@@ -1051,7 +1051,7 @@
1051
1051
  "cell_type": "markdown",
1052
1052
  "metadata": {},
1053
1053
  "source": [
1054
- "You can also use pandas to export the data to a CSV (comma separated value), which can be opened by any common spreadsheet application or opened by pandas.\n",
1054
+ "You can also use pandas to export the data to a CSV (comma separated value) file, which can be opened by any common spreadsheet application or opened by pandas.\n",
1055
1055
  "\n",
1056
1056
  "If you do not specify a file path, the file will be saved in the local directory. After you run the code below you will see two files appear (*model_data.csv* and *agent_data.csv*)"
1057
1057
  ]
@@ -1280,7 +1280,7 @@
1280
1280
  "\n",
1281
1281
  "**Model-specific implementation:** In this case we will give agents an attribute of enthnicity of Green, Blue or Mixed. Green and Blue agents only give money to their ethnicity while Mixed can give money to anyone.\n",
1282
1282
  "\n",
1283
- "**Code Implementation**: Using `groupby` we will execute the above logic in our code passing a list of grouped agents into our `give_money` function. To ensure we can plot wealth by group we also need to add ethnicity to our datacollector. "
1283
+ "**Code Implementation**: Using `groupby` we will execute the above logic in our code by passing a list of grouped agents into our `give_money` function. To ensure we can plot wealth by group we also need to add ethnicity to our datacollector. "
1284
1284
  ]
1285
1285
  },
1286
1286
  {
@@ -1460,7 +1460,7 @@
1460
1460
  " A dictionary containing all the parameters of the model class and desired values to use for the batch run as key-value pairs. Each value can either be fixed ( e.g. `{\"height\": 10, \"width\": 10}`) or an iterable (e.g. `{\"n\": range(10, 500, 10)}`). `batch_run` will then generate all possible parameter combinations based on this dictionary and run the model `iterations` times for each combination.\n",
1461
1461
  "* `number_processes`\n",
1462
1462
  " If not specified, defaults to 1. Set it to `None` to use all the available processors.\n",
1463
- " note: Multiprocessing does make debugging challenging. If your parameter sweeps are resulting in unexpected errors set `number_processes=1`.\n",
1463
+ " Note: Multiprocessing does make debugging challenging. If your parameter sweeps are resulting in unexpected errors set `number_processes=1`.\n",
1464
1464
  "* `iterations`\n",
1465
1465
  " The number of iterations to run each parameter combination for. Optional. If not specified, defaults to 1.\n",
1466
1466
  "* `data_collection_period`\n",
@@ -1482,16 +1482,16 @@
1482
1482
  "1. the Gini coefficient value at each time step, and\n",
1483
1483
  "2. the individual agent's wealth development and steps without giving money.\n",
1484
1484
  "\n",
1485
- "**Important:** Since for the latter changes at each time step might be interesting, we set `data_collection_period=1`. By default, it only collects data at the end of each episode.\n",
1485
+ "**Important:** Since for the latter, changes at each time step might be interesting, we set `data_collection_period=1`. By default, it only collects data at the end of each episode.\n",
1486
1486
  "\n",
1487
- "note: The total number of runs is 245 (= 49 different populations * 5 iterations per population). However, the resulting list of dictionaries will be of length 6186250 (= 250 average agents per population * 49 different populations * 5 iterations per population * 101 steps per iteration). "
1487
+ "Note: The total number of runs is 245 (= 49 different populations * 5 iterations per population). However, the resulting list of dictionaries will be of length 6186250 (= 250 average agents per population * 49 different populations * 5 iterations per population * 101 steps per iteration). "
1488
1488
  ]
1489
1489
  },
1490
1490
  {
1491
1491
  "cell_type": "markdown",
1492
1492
  "metadata": {},
1493
1493
  "source": [
1494
- "**note for Windows OS users:** If you are running this tutorial in Jupyter, make sure that you set `number_processes = 1` (single process). If `number_processes` is greater than 1, it is less straightforward to set up. For details on how to use multiprocessing on windows, see [multiprocessing's programming guidelines](https://docs.python.org/3/library/multiprocessing.html#multiprocessing-programming). "
1494
+ "**Note for Windows OS users:** If you are running this tutorial in Jupyter, make sure that you set `number_processes = 1` (single process). If `number_processes` is greater than 1, it is less straightforward to set up. For details on how to use multiprocessing on windows, see [multiprocessing's programming guidelines](https://docs.python.org/3/library/multiprocessing.html#multiprocessing-programming). "
1495
1495
  ]
1496
1496
  },
1497
1497
  {
@@ -1541,7 +1541,7 @@
1541
1541
  "cell_type": "markdown",
1542
1542
  "metadata": {},
1543
1543
  "source": [
1544
- "First, we want to take a closer look at how the Gini coefficient at the end of each episode changes as we increase the size of the population. For this, we filter our results to only contain the data of one agent (the Gini coefficient will be the same for the entire population at any time) at the 100th step of each episode and then scatter-plot the values for the Gini coefficient over the the number of agents. notice there are five values for each population size since we set `iterations=5` when calling the batch run."
1544
+ "First, we want to take a closer look at how the Gini coefficient at the end of each episode changes as we increase the size of the population. For this, we filter our results to only contain the data of one agent (the Gini coefficient will be the same for the entire population at any time) at the 100th step of each episode and then scatter-plot the values for the Gini coefficient over the the number of agents. Notice there are five values for each population size since we set `iterations=5` when calling the batch run."
1545
1545
  ]
1546
1546
  },
1547
1547
  {
@@ -1600,7 +1600,7 @@
1600
1600
  "cell_type": "markdown",
1601
1601
  "metadata": {},
1602
1602
  "source": [
1603
- "Second, we want to display the agent's wealth at each time step of one specific episode. To do this, we again filter our large data frame, this time with a fixed number of agents and only for a specific iteration of that population.\n",
1603
+ "Secondly, we want to display the agent's wealth at each time step of one specific episode. To do this, we again filter our large data frame, this time with a fixed number of agents and only for a specific iteration of that population.\n",
1604
1604
  "To print the results, we convert the filtered data frame to a string specifying the desired columns to print. \n",
1605
1605
  "\n",
1606
1606
  "Pandas has built-in functions to convert to a lot of different data formats. For example, to display as a table in a Jupyter notebook, we can use the `to_html()` function which takes the same arguments as `to_string()` (see commented lines)."
@@ -1656,7 +1656,7 @@
1656
1656
  "### Analyzing model reporters: Comparing 5 scenarios\n",
1657
1657
  "Other insights might be gathered when we compare the Gini coefficient of different scenarios. For example, we can compare the Gini coefficient of a population with 25 agents to the Gini coefficient of a population with 400 agents. While doing this, we increase the number of iterations to 25 to get a better estimate of the Gini coefficient for each population size and get usable error estimations.\n",
1658
1658
  "\n",
1659
- "As we look varying the parameters to see the impact on model outcomes, it is critical to again point that users can set the random seed. Due to the often inherent randomness with ABMs the seed becomes crucial for: \n",
1659
+ "As we look varying the parameters to see the impact on model outcomes, it is critical to again point out that users can set the random seed. Due to the often inherent randomness with ABMs the seed becomes crucial for: \n",
1660
1660
  "- **Reproducibility** - Being able to replicate the ABM results\n",
1661
1661
  "- **Sensitivity Analysis** - Identifying how sensitive/robust your model results are to random fluctuations\n",
1662
1662
  "\n",
@@ -128,13 +128,13 @@
128
128
  "outputs": [],
129
129
  "source": [
130
130
  "# Create initial model instance\n",
131
- "model1 = MoneyModel(n=50, width=10, height=10) #keyword arguments\n",
131
+ "money_model = MoneyModel(n=50, width=10, height=10) #keyword arguments\n",
132
132
  "\n",
133
133
  "SpaceGraph = make_space_component(agent_portrayal)\n",
134
134
  "GiniPlot = make_plot_component(\"Gini\")\n",
135
135
  "\n",
136
136
  "page = SolaraViz(\n",
137
- " model1,\n",
137
+ " money_model,\n",
138
138
  " components=[SpaceGraph, GiniPlot],\n",
139
139
  " model_params=model_params,\n",
140
140
  " name=\"Boltzmann Wealth Model\",\n",
@@ -207,13 +207,13 @@
207
207
  "outputs": [],
208
208
  "source": [
209
209
  "# Create initial model instance\n",
210
- "model = MoneyModel(n=50, width=10, height=10)\n",
210
+ "money_model = MoneyModel(n=50, width=10, height=10)\n",
211
211
  "\n",
212
212
  "SpaceGraph = make_space_component(agent_portrayal)\n",
213
213
  "GiniPlot = make_plot_component(\"Gini\")\n",
214
214
  "\n",
215
215
  "page = SolaraViz(\n",
216
- " model1,\n",
216
+ " money_model,\n",
217
217
  " components=[SpaceGraph, GiniPlot],\n",
218
218
  " model_params=model_params,\n",
219
219
  " name=\"Boltzmann Wealth Model\",\n",
@@ -318,7 +318,7 @@
318
318
  "outputs": [],
319
319
  "source": [
320
320
  "# Create initial model instance\n",
321
- "model = MoneyModel(n=50, width=10, height=10)\n",
321
+ "money_model = MoneyModel(n=50, width=10, height=10)\n",
322
322
  "\n",
323
323
  "SpaceGraph = make_space_component(agent_portrayal)\n",
324
324
  "GiniPlot = make_plot_component(\"Gini\")"
@@ -354,7 +354,7 @@
354
354
  ],
355
355
  "source": [
356
356
  "page = SolaraViz(\n",
357
- " model,\n",
357
+ " money_model,\n",
358
358
  " components=[SpaceGraph, GiniPlot, Histogram],\n",
359
359
  " model_params=model_params,\n",
360
360
  " name=\"Boltzmann Wealth Model\",\n",
@@ -399,7 +399,7 @@
399
399
  }
400
400
  ],
401
401
  "source": [
402
- "Histogram(model)"
402
+ "Histogram(money_model)"
403
403
  ]
404
404
  },
405
405
  {
@@ -22,7 +22,7 @@ __all__ = [
22
22
  ]
23
23
 
24
24
  __title__ = "mesa"
25
- __version__ = "3.1.1"
25
+ __version__ = "3.1.3"
26
26
  __license__ = "Apache 2.0"
27
27
  _this_year = datetime.datetime.now(tz=datetime.UTC).date().year
28
28
  __copyright__ = f"Copyright {_this_year} Project Mesa Team"
@@ -0,0 +1,183 @@
1
+ {
2
+ "cells": [
3
+ {
4
+ "cell_type": "markdown",
5
+ "metadata": {},
6
+ "source": [
7
+ "# Demographic Prisoner's Dilemma\n",
8
+ "\n",
9
+ "The Demographic Prisoner's Dilemma is a family of variants on the classic two-player [Prisoner's Dilemma](https://en.wikipedia.org/wiki/Prisoner's_dilemma), first developed by [Joshua Epstein](http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.8.8629&rep=rep1&type=pdf). The model consists of agents, each with a strategy of either Cooperate or Defect. Each agent's payoff is based on its strategy and the strategies of its spatial neighbors. After each step of the model, the agents adopt the strategy of their neighbor with the highest total score. \n",
10
+ "\n",
11
+ "The specific variant presented here is adapted from the [Evolutionary Prisoner's Dilemma](http://ccl.northwestern.edu/netlogo/models/PDBasicEvolutionary) model included with NetLogo. Its payoff table is a slight variant of the traditional PD payoff table:\n",
12
+ "\n",
13
+ "<table>\n",
14
+ " <tr><td></td><td>**Cooperate**</td><td>**Defect**</td></tr>\n",
15
+ " <tr><td>**Cooperate**</td><td>1, 1</td><td>0, *D*</td></tr>\n",
16
+ " <tr><td>**Defect**</td><td>*D*, 0</td><td>0, 0</td></tr>\n",
17
+ "</table>\n",
18
+ "\n",
19
+ "Where *D* is the defection bonus, generally set higher than 1. In these runs, the defection bonus is set to $D=1.6$.\n",
20
+ "\n",
21
+ "The Demographic Prisoner's Dilemma demonstrates how simple rules can lead to the emergence of widespread cooperation, despite the Defection strategy dominiating each individual interaction game. However, it is also interesting for another reason: it is known to be sensitive to the activation regime employed in it.\n",
22
+ "\n",
23
+ "Below, we demonstrate this by instantiating the same model (with the same random seed) three times, with three different activation regimes: \n",
24
+ "\n",
25
+ "* Sequential activation, where agents are activated in the order they were added to the model;\n",
26
+ "* Random activation, where they are activated in random order every step;\n",
27
+ "* Simultaneous activation, simulating them all being activated simultaneously.\n",
28
+ "\n"
29
+ ]
30
+ },
31
+ {
32
+ "cell_type": "code",
33
+ "metadata": {},
34
+ "source": [
35
+ "import matplotlib.pyplot as plt\n",
36
+ "from model import PdGrid\n",
37
+ "\n",
38
+ "%matplotlib inline"
39
+ ],
40
+ "outputs": [],
41
+ "execution_count": null
42
+ },
43
+ {
44
+ "cell_type": "markdown",
45
+ "metadata": {},
46
+ "source": [
47
+ "## Helper functions"
48
+ ]
49
+ },
50
+ {
51
+ "cell_type": "code",
52
+ "metadata": {},
53
+ "source": [
54
+ "from mesa.visualization.mpl_space_drawing import draw_space\n",
55
+ "\n",
56
+ "\n",
57
+ "def agent_portroyal(agent):\n",
58
+ " return {\"color\": \"red\" if agent.move == \"D\" else \"blue\", \"marker\": \"s\", \"size\": 11}"
59
+ ],
60
+ "outputs": [],
61
+ "execution_count": null
62
+ },
63
+ {
64
+ "cell_type": "code",
65
+ "metadata": {},
66
+ "source": [
67
+ "def run_model(model):\n",
68
+ " \"\"\"\n",
69
+ " Run an experiment with a given model, and plot the results.\n",
70
+ " \"\"\"\n",
71
+ " fig = plt.figure(figsize=(12, 8))\n",
72
+ "\n",
73
+ " ax1 = fig.add_subplot(231)\n",
74
+ " ax2 = fig.add_subplot(232)\n",
75
+ " ax3 = fig.add_subplot(233)\n",
76
+ " ax4 = fig.add_subplot(212)\n",
77
+ "\n",
78
+ " draw_space(model.grid, agent_portroyal, ax=ax1, draw_grid=False)\n",
79
+ " model.run(10)\n",
80
+ " draw_space(model.grid, agent_portroyal, ax=ax2, draw_grid=False)\n",
81
+ " model.run(10)\n",
82
+ " draw_space(model.grid, agent_portroyal, ax=ax3, draw_grid=False)\n",
83
+ " model.datacollector.get_model_vars_dataframe().plot(ax=ax4)"
84
+ ],
85
+ "outputs": [],
86
+ "execution_count": null
87
+ },
88
+ {
89
+ "cell_type": "code",
90
+ "metadata": {},
91
+ "source": [
92
+ "# Set the random seed\n",
93
+ "seed = 21"
94
+ ],
95
+ "outputs": [],
96
+ "execution_count": null
97
+ },
98
+ {
99
+ "cell_type": "markdown",
100
+ "metadata": {},
101
+ "source": [
102
+ "## Sequential Activation"
103
+ ]
104
+ },
105
+ {
106
+ "cell_type": "code",
107
+ "metadata": {},
108
+ "source": [
109
+ "pd_model = PdGrid(50, 50, \"Sequential\", seed=seed)\n",
110
+ "run_model(pd_model)"
111
+ ],
112
+ "outputs": [],
113
+ "execution_count": null
114
+ },
115
+ {
116
+ "cell_type": "markdown",
117
+ "metadata": {},
118
+ "source": [
119
+ "## Random Activation"
120
+ ]
121
+ },
122
+ {
123
+ "cell_type": "code",
124
+ "metadata": {},
125
+ "source": [
126
+ "pd_model = PdGrid(50, 50, \"Random\", seed=seed)\n",
127
+ "run_model(pd_model)"
128
+ ],
129
+ "outputs": [],
130
+ "execution_count": null
131
+ },
132
+ {
133
+ "cell_type": "markdown",
134
+ "metadata": {
135
+ "collapsed": true,
136
+ "jupyter": {
137
+ "outputs_hidden": true
138
+ }
139
+ },
140
+ "source": [
141
+ "## Simultaneous Activation"
142
+ ]
143
+ },
144
+ {
145
+ "cell_type": "code",
146
+ "metadata": {},
147
+ "source": [
148
+ "pd_model = PdGrid(50, 50, \"Simultaneous\", seed=seed)\n",
149
+ "run_model(pd_model)"
150
+ ],
151
+ "outputs": [],
152
+ "execution_count": null
153
+ },
154
+ {
155
+ "cell_type": "code",
156
+ "metadata": {},
157
+ "source": [],
158
+ "outputs": [],
159
+ "execution_count": null
160
+ }
161
+ ],
162
+ "metadata": {
163
+ "kernelspec": {
164
+ "display_name": "Python 3 (ipykernel)",
165
+ "language": "python",
166
+ "name": "python3"
167
+ },
168
+ "language_info": {
169
+ "codemirror_mode": {
170
+ "name": "ipython",
171
+ "version": 3
172
+ },
173
+ "file_extension": ".py",
174
+ "mimetype": "text/x-python",
175
+ "name": "python",
176
+ "nbconvert_exporter": "python",
177
+ "pygments_lexer": "ipython3",
178
+ "version": "3.11.0"
179
+ }
180
+ },
181
+ "nbformat": 4,
182
+ "nbformat_minor": 4
183
+ }