villager
villager: A framework for designing and executing agent-based models in R - Published in JOSS (2022)
Science Score: 95.0%
This score indicates how likely this project is to be science-related based on various indicators:
-
○CITATION.cff file
-
✓codemeta.json file
Found codemeta.json file -
✓.zenodo.json file
Found .zenodo.json file -
✓DOI references
Found 4 DOI reference(s) in README and JOSS metadata -
✓Academic publication links
Links to: joss.theoj.org -
✓Committers with academic emails
1 of 4 committers (25.0%) from academic institutions -
○Institutional organization owner
-
✓JOSS paper metadata
Published in Journal of Open Source Software
Keywords
Repository
villager is an extensible agent based modeling (ABM) framework for the R language. It supports agents, agent aggregations and their associated resources, as well as flexible data management.
Basic Info
Statistics
- Stars: 58
- Watchers: 2
- Forks: 6
- Open Issues: 2
- Releases: 6
Topics
Metadata Files
README.md
villager 
villager is a framework for creating and running agent based models in R. Its purpose is to provide an extensible framework where modeling can be done in native R.
Features
- Extensible data output system (csv, excel sheets, sqlite)
- Built in support for agents and resources
- Easy to use time management
Installing
villager can be installed from CRAN by running the following,
install.packages("villager")
Takeaways
When reading though the Readme and vignettes, it's important to take note of a few concepts
- Villages are the highest aggregate; they contain villages which in turn contain agents (agents)
- Agents and resources can be subclassed to support additional properties
- The data_writer class can be subclassed when writing to data sources other than csv
- Models are functions that are added to villages; each village can exhibit different behavior
Using villager
villager is about modeling populations with (optional) associated resources. It supports a community level aggregation of agents, referred to as villages or an individual village. Agents, which are referred to as gender-neutral agents, are members of community level aggregations.
villager compliant models must conform to the function template below. The agent_mgr and resource_mgr are responsible for interacting with the individual agents and resources.
{r}
test_model <- function(current_state, previous_state, model_data, agent_mgr, resource_mgr) {
...
...
}
Creating & Managing Agents
Agents are created by instantiating the agent class. There are a number of agent properties that can be passed to the constructor.
{r}
test_model <- function(current_state, previous_state, model_data, agent_mgr, resource_mgr, village_mgr) {
mother <- agent$new(first_name="Kirsten", last_name="Taylor", age=9125)
father <- agent$new(first_name="Joshua", last_name="Thompson", age=7300)
daughter <- agent$new(first_name="Mariylyyn", last_name="Thompson", age=10220)
}
To add agents to the simulation, use the provided agent_mgr object to call add_agent. Because the classes are R6, the object can be modified after being added to the manager and the changes will be persisted without needing to re-add the villager. For example, setting a daughter's mother and her father below. Note that the standard way is to modify the properties beforehand, although not strictly necessary.
{r}
test_model <- function(current_state, previous_state, model_data, agent_mgr, resource_mgr, village_mgr) {
agent_mgr <- agent_manager$new()
agent_mgr$add_agent(mother, father, daughter)
daughter$mother_id <- mother$identifier
daughter$father_id <- father$identifier
}
The agent manager can also be used to pair agents, representative of a relationship or social bond.
agent_mgr$agent_mgr$connect_agents(mother, father)
Creating & Managing Resources
Resources are similar to agents in that they're both R6 classes, are instantiated similarly, and are also managed by an object passed into the model. An example of creating resources and adding them to the simulation is given below.
``` testmodel <- function(currentstate, previousstate, modeldata, agentmgr, resourcemgr, villagemgr) { cornresource <- resource$new(name="corn", quantity = 10) fishresource <- resource$new(name="fish", quantity = 15) cornresource$quantity=5
resourcemgr <- resourcemanager$new() resourcemgr$addresource(cornresource, fishresource) fish_resource$quantity=5 } ```
State
Objects of type village, agent, and resourcehave particular states at a particular time. As the simulation progresses, the state of these change based on model logic. At the end of each time step, the state of each object is saved, giving a complete record of the system's evolution. The essence of any agent based model is changing the state at each time step. villager provides a mechanism for defining the initial state and for changing the state throughout the simulation.
Managing the Initial State
Creating the initial state is done by creating a function that resembles model functions from above. The manager classes are used to populate the village with an initial population of agents and resources.
``` initialcondition <- function(currentstate, modeldata, agentmgr, resourcemgr) { # Create the initial villagers mother <- agent$new(firstname="Kirsten", lastname="Taylor", age=9125) father <- agent$new(firstname="Joshua", lastname="Thompson", age=7300) daughter <- agent$new(firstname="Mariylyyn", lastname="Thompson", age=10220) daughter$motherid <- mother$identifier daughter$father_id <- father$identifier
# Add the agents to the manager agentmgr$connectagents(mother, father) agentmgr$addagent(mother, father, daughter)
# Create the resources cornresource <- resource$new(name="corn", quantity = 10) fishresource <- resource$new(name="fish", quantity = 15)
# Add the resources to the manager resourcemgr$addresource(cornresource, fishresource) } ```
Creating Villages and Running Models
Models are tied to particular village instances. This binding is done when villages are created, shown below. Models can have names and must always be paired with an initial condition function and a model function.
{r}
small_village <- village$new("Test Model 1", initial_condition, test_model)
The simulator class is responsible for running simulations. It encapsulates all of the villages and controls the duration of the simulation. The simulator below runs for 100 time steps: roughly 13 years. The simulator can be paired with any number of villages, in the case of the simulator below, there's only a single village.
simulator <- simulation$new(100, list(small_village))
simulator$run_model()
Example: A small village with a single family
We can combine the examples above into a full simulation that...
- Starts with an initial population of three villagers
- Increases the age of each villager at the start of each day
- Runs for 4745 days
- Sets the villager profession after age 12
```{r} library(villager) initialcondition <- function(currentstate, modeldata, agentmgr, resourcemgr) { # Create the initial villagers mother <- agent$new(firstname="Kirsten", lastname="Taylor", age=9125) father <- agent$new(firstname="Joshua", lastname="Thompson", age=7300) daughter <- agent$new(firstname="Mariylyyn", lastname="Thompson", age=10220) daughter$motherid <- mother$identifier daughter$father_id <- father$identifier
# Add the agents to the manager agentmgr$connectagents(mother, father) agentmgr$addagent(mother, father, daughter)
# Create the resources cornresource <- resource$new(name="corn", quantity = 10) fishresource <- resource$new(name="fish", quantity = 15)
# Add the resources to the manager resourcemgr$addresource(cornresource, fishresource) }
testmodel <- function(currentstate, previousstate, modeldata, agentmgr, resourcemgr, villagemgr) { print(paste("Step:", currentstate$step)) for (agent in agentmgr$getliving_agents()) { agent$age <- agent$age+1 if (agent$age >= 4383) { agent$profession <- "Farmer" } } }
smallvillage <- village$new("Test Model", initialcondition, testmodel) simulator <- simulation$new(4745, list(smallvillage)) simulator$run_model() ```
Example: Creating new villagers
To demonstrate programatically creating villagers, consider the model below that has the following logic.
- Starts with 10 villagers
- Every even day, two new villagers are created
- Every odd day, one villager dies
``` initialcondition <- function(currentstate, modeldata, agentmgr, resourcemgr) { for (i in 1:10) { name <- runif(1, 0.0, 100) newagent <- agent$new(firstname <- name, lastname <- "Smith") agentmgr$addagent(new_agent) } }
model <- function(currentstate, previousstate, modeldata, agentmgr, resourcemgr, villagemgr) { currentday <- currentstate$step if((currentday%%2) == 0) { # Then it's an even day # Create two new agents whose first names are random numbers for (i in 1:2) { name <- runif(1, 0.0, 100) newagent <- agent$new(firstname <- name, lastname <- "Smith") agentmgr$addagent(newagent) } } else { # It's an odd day livingagents <- agentmgr$getlivingagents() # Kill the first one livingagents[[1]]$alive <- FALSE } } coastalvillage <- village$new("Test village", initialcondition, model) simulator <- simulation$new(4, villages = list(coastalvillage)) simulator$runmodel() ```
Advanced Usage
In the examples above, the default properties of agents and resources were used. It's possible that these won't cover all the needs for more diverse models. There are vignettes on extending the agent and resource classes to handle these situations.
Contributing
Code contributions are welcome as pull requests to the develop branch. Bugs, comments, and questions can be submitted as Github Issues.
Owner
- Name: Marcus Thomson
- Login: zizroc
- Kind: user
- Location: Irvine, California
- Company: Sequoia Climate Foundation
- Repositories: 3
- Profile: https://github.com/zizroc
JOSS Publication
villager: A framework for designing and executing agent-based models in R
Authors
College of Creative Studies, University of California, Santa Barbara
Department of Anthropology, University of California, Santa Barbara
Tags
agent based modeling simulation frameworkGitHub Events
Total
- Watch event: 3
Last Year
- Watch event: 3
Committers
Last synced: 5 months ago
Top Committers
| Name | Commits | |
|---|---|---|
| Thomas Thelen | t****n@g****m | 112 |
| Marcus Thomson | 3****c | 11 |
| ohmannyy | m****y@u****u | 6 |
| gvaldana | 6****a | 2 |
Committer Domains (Top 20 + Academic)
Issues and Pull Requests
Last synced: 4 months ago
All Time
- Total issues: 57
- Total pull requests: 41
- Average time to close issues: 4 months
- Average time to close pull requests: 9 days
- Total issue authors: 4
- Total pull request authors: 4
- Average comments per issue: 1.16
- Average comments per pull request: 0.49
- Merged pull requests: 39
- Bot issues: 0
- Bot pull requests: 0
Past Year
- Issues: 0
- Pull requests: 0
- Average time to close issues: N/A
- Average time to close pull requests: N/A
- Issue authors: 0
- Pull request authors: 0
- Average comments per issue: 0
- Average comments per pull request: 0
- Merged pull requests: 0
- Bot issues: 0
- Bot pull requests: 0
Top Authors
Issue Authors
- ThomasThelen (50)
- zizroc (4)
- thodson-usgs (2)
- Edouard-Legoupil (1)
Pull Request Authors
- ThomasThelen (38)
- zizroc (2)
- ohmannyy (2)
- thodson-usgs (1)
Top Labels
Issue Labels
Pull Request Labels
Packages
- Total packages: 1
-
Total downloads:
- cran 208 last-month
- Total dependent packages: 0
- Total dependent repositories: 0
- Total versions: 2
- Total maintainers: 1
cran.r-project.org: villager
A Framework for Designing and Running Agent Based Models
- Homepage: https://github.com/zizroc/villager/
- Documentation: http://cran.r-project.org/web/packages/villager/villager.pdf
- License: MIT + file LICENSE
-
Latest release: 2.0.0
published over 1 year ago
Rankings
Maintainers (1)
Dependencies
- R >= 3.5.0 depends
- R6 * imports
- readr * imports
- uuid * imports
- covr * suggests
- dplyr * suggests
- knitr * suggests
- leaflet * suggests
- plotly * suggests
- remotes * suggests
- rmarkdown * suggests
- testthat * suggests
- actions/checkout v2 composite
- actions/upload-artifact main composite
- r-lib/actions/check-r-package v1 composite
- r-lib/actions/setup-pandoc v1 composite
- r-lib/actions/setup-r v2 composite
- r-lib/actions/setup-r-dependencies v1 composite
- actions/checkout v2 composite
- r-lib/actions/setup-r v2 composite
- r-lib/actions/setup-r-dependencies v1 composite
