{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "Netlogo is often run from its own GUI, but it can also be run 'headless'; that is to say, run from the command line or from within another program, in the background. That is what we are doing here from this notebook. We will use the [NLRX package](https://nldoc.github.io/nlrx/) to interface between R and Netlogo. This gives us the advantage of gathering data for analysis within R while running models written in the nlogo language. We can write models using Python or other langugages, but Netlogo's language is particularly well-suited for agent modeling. This notebook recreates the spatial output walkthrough at [nldoc.github.io site](https://nldoc.github.io/nlrx/articles/articles/spatial-output.html)." ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [], "source": [ "library(\"magrittr\")\n", "library(\"raster\")\n", "library(\"furrr\")" ] }, { "cell_type": "code", "execution_count": 15, "metadata": {}, "outputs": [], "source": [ "# this package was installed during the creation of the binder\n", "# if you get an error running this line:\n", "library(\"nlrx\", lib.loc=\"/srv/rlibs\")\n", "\n", "# insert the following line into a block *above* this one, remove the #, and then run it:\n", "# devtools::install_github(\"nldoc/nlrx\")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We create a variable, `nl`, that tells the package where to find Netlogo (which we installed when we built this binder), where to find the model, written in `nlogo` code, and how much memory to set aside for the java virtual machine that will run the model." ] }, { "cell_type": "code", "execution_count": 16, "metadata": {}, "outputs": [], "source": [ "nl <- nl(nlversion = \"6.0.4\",\n", " nlpath = \"/home/jovyan/NetLogo 6.0.4/\",\n", " modelpath = \"/home/jovyan/NetLogo 6.0.4/app/models/Sample Models/Biology/Wolf Sheep Predation.nlogo\",\n", " jvmmem = 1024)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now, let's define the experiment that we are going to run, by specifying all of the various parameters available in the model." ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [], "source": [ "nl@experiment <- experiment(expname = \"nlrx_spatial\",\n", " outpath=\"out/\",\n", " repetition = 1, \n", " tickmetrics = \"true\",\n", " idsetup = \"setup\", \n", " idgo = \"go\", \n", " idfinal = NA_character_, \n", " idrunnum = NA_character_,\n", " runtime = 100,\n", " evalticks = seq(1,100),\n", " metrics = c(\"count sheep\",\"count wolves\"),\n", " metrics.turtles = c(\"who\", \"pxcor\", \"pycor\", \"breed\"),\n", " metrics.patches = c(\"pxcor\", \"pycor\", \"pcolor\"),\n", " constants = list(\"model-version\" = \"\\\"sheep-wolves-grass\\\"\",\n", " 'initial-number-sheep' = 100,\n", " 'initial-number-wolves' = 50,\n", " \"grass-regrowth-time\" = 30,\n", " \"sheep-gain-from-food\" = 4,\n", " \"wolf-gain-from-food\" = 20,\n", " \"sheep-reproduce\" = 4,\n", " \"wolf-reproduce\" = 5,\n", " \"show-energy?\" = \"false\")\n", " )" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "From the nlrx package documentation: \"While the experiment defines the variables and specifications of the model, the simulation design creates a parameter input table based on these model specifications and the chosen simulation design method. nlrx provides a bunch of different simulation designs, such as full-factorial, latin-hypercube, sobol, morris and eFast. A simulation design is attached to a nl object by using one of these simdesign functions:\"" ] }, { "cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "Creating simple simulation design\n" ] } ], "source": [ "nl@simdesign <- simdesign_simple(nl=nl,\n", " nseeds=1)\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This experiment will run for 100 ticks and collects all metrics, metrics.turtles and metrics.patches on each tick. Thus, running run_nl_all() will report a tibble containing all metrics, metrics.turtles and metrics.patches. However, because the spatial metrics contain more than one value, these datasets are stored as lists inside the output tibble. This lists already contain all measured agent metrics and can for example be used to analyse distributions of these variables for specific agent groups.\n", "\n", "In case of spatial data containing coordinates (pxcor/pycor for patches or pxcor/pycor and/or xcor/ycor for turtles), nlrx provides a function to transform the measured output into spatial objects. In order to use the function get_nl_spatial() you first have to attach your simulation output results to the nl object:" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [], "source": [ "future::plan(multisession)\n", "results %<-% run_nl_all(nl = nl, cleanup = \"all\")" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ "Warning message in eval(expr, envir, enclos):\n", "“restarting interrupted promise evaluation”" ] }, { "ename": "ERROR", "evalue": "Error: Expressions are currently not supported in `rename()`\n", "output_type": "error", "traceback": [ "Error: Expressions are currently not supported in `rename()`\nTraceback:\n", "1. local({\n . value <- value(future)\n . rm(list = future_name, envir = assign.env)\n . value\n . })", "2. eval.parent(substitute(eval(quote(expr), envir)))", "3. eval(expr, p)", "4. eval(expr, p)", "5. eval(quote({\n . value <- value(future)\n . rm(list = future_name, envir = assign.env)\n . value\n . }), new.env())", "6. eval(quote({\n . value <- value(future)\n . rm(list = future_name, envir = assign.env)\n . value\n . }), new.env())", "7. value(future)", "8. value.Future(future)", "9. resignalCondition(future)" ] } ], "source": [ "\n", "# Attach results to nl object:\n", "setsim(nl, \"simoutput\") <- results\n", "\n", "# Report spatial data:\n", "results_spatial <- get_nl_spatial(nl,\n", " turtles = TRUE,\n", " patches = TRUE,\n", " turtle_coords = \"px\",\n", " format=\"spatial\")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The get_nl_spatial() function uses 4 function parameters:\n", "\n", "turtles - TRUE/FALSE, if true the function will transform the measured metrics.turtles to spatial sf objects.\n", "patches - TRUE/FALSE, if true the function will transform the measured metrics.patches to spatial raster objects. In case there are several patches variables besides the coordinates, the result will be a rasterstack containing one raster for each patch variable\n", "turtle_coords - “px”/“x”, because turtle coordinates can be measured as pxcor/pycor or xcor/ycor this string defines which coordinates are used for creating the turtle sf objects. For instance, you can measure both coordinate pairs by entering them into metrics.turtles, and then decide for one type of coordinates to create spatial objects.\n", "format - “spatial”/“tibble”, the “spatial” option will report the generated output as tibble containing the spatial objects (raster/rasterStack, sf). You can also choose format “tibble” report the spatial objects as a long format tibble, that can be used for plotting landscapes and turtles with ggplot2.\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] } ], "metadata": { "kernelspec": { "display_name": "R", "language": "R", "name": "ir" }, "language_info": { "codemirror_mode": "r", "file_extension": ".r", "mimetype": "text/x-r-source", "name": "R", "pygments_lexer": "r", "version": "3.4.4" } }, "nbformat": 4, "nbformat_minor": 2 }