ropensci / nlrx

nlrx NetLogo R
https://docs.ropensci.org/nlrx
GNU General Public License v3.0
77 stars 12 forks source link

How to set strings/factors in `experiment()`? #2

Closed z3tt closed 6 years ago

z3tt commented 6 years ago

Thanks for this incredibly easy way to call NetLogo from R, what a nice improvement of the hustle of RNetLogo.

However, I struggle to enter strings or factors as variables when setting up an experiment using the experiment() command. The documentation says that "Each list item consist of a min value, a max value, a step value and a qfun (e.g. list("paramA" = list(min=0, max=1, step=0.1, qfun="qunif")))" which is not the case for strings/factors. Every way putting the strings in a list did result in an error asking for 'from' must be of length 1.

Is there a way to set up strings/factors as input variables?

nldoc commented 6 years ago

Currently, the variables slot only takes numeric inputs. When I implemented this, I only had sensitivity analyses in mind, which of course only work properly for numeric parameters. However, at least for the simple and full factorial simdesign it would be theoretical possible to include strings as parameter values. Thus, I plan to implement an option which allows to also supply discrete values for parameters within the variables slot. Instead of defining min, max, step and a qfun you could then just provide distinct values. I hope to get this implemented in the next days.

z3tt commented 6 years ago

Hi, thanks for your effort! I got your point but from what I've learned it a full sensitivity analysis should be also possible with a combination of both, numeric and factorial variables. Would be great if the lhs sampling would still l work when using factors (very nice btw to implement those different in the package, thumbs up).

On Tue, Aug 14, 2018, 11:15 nldoc notifications@github.com wrote:

Currently, the variables slot only takes numeric inputs. When I implemented this, I only had sensitivity analyses in mind, which of course only work properly for numeric parameters. However, at least for the simple and full factorial simdesign it would be theoretical possible to include strings as parameter values. Thus, I plan to implement an option which allows to also supply discrete values for parameters within the variables slot. Instead of defining min, max, step and a qfun you could then just provide distinct values. I hope to get this implemented in the next days.

— You are receiving this because you authored the thread. Reply to this email directly, view it on GitHub https://github.com/nldoc/nlrx/issues/2#issuecomment-412807985, or mute the thread https://github.com/notifications/unsubscribe-auth/AHLM5Iy3lhgbC6NXG2wMkyh02DFGKq7cks5uQpUigaJpZM4V8BO- .

nldoc commented 6 years ago

Please check out the latest update. But please note that not all functions are tested thoroughly. I am still working on the latest updates. For the simdesign_ff it is now also possible to provide distinct values for each variable (further details, see readme of this repository). This also supports categorical values, such as strings. I also added a new simdesign (simdesign_distinct). For this simdesign you define a vector of n values for each variable. The parameter matrix then combines all first items of these vectors to one parameterisation, then all second items, and so on. This also supports categorical values.

However, I am still struggling with the categorical lhs. It would be possible by transforming the distributions to distinct factor levels but this seems not to be straightforward. As a quick fix, you could manage this within your NetLogo model. Just create numeric sliders on your GUI and add them to the variables of your experiment. In your NetLogo model you can then set your factors based on these numeric values.

z3tt commented 6 years ago

Hi, I now had time to check the updates. Providing factors works (e.g. 'initial-number-sheep' = list(values=c("\"LOW", "\"HIGH\"")) and I am also able to run simulations but only using the simdesign_simple() function. Thanks for the update!

But simdesign_distinct() and simdesign_ff() both result in an error when running run_nl_all(nl = nl, cleanup = "all"):

Error in $<-.data.frame(*tmp*, "siminputrow", value = 1L) : replacement has 1 row, data has 0

I am not sure why this is the case. You can find the toy model (adapted wolf sheep model) I used to test it here: https://ufile.io/dkr50. The code to set up and run the design I used is:

library(nlrx)
library(future)

nl <- nl(nlversion = "6.0.4",
         nlpath = "C:/Program Files/NetLogo6.0.4/",
         modelpath = "C:/Program Files/NetLogo6.0.4/app/models/Sample Models/Biology/Wolf Sheep Predation_mod.nlogo",
         jvmmem = 1024)

nl@experiment <- experiment(expname = "wolf-sheep",
                            outpath = "C:/out/",
                            repetition = 1,
                            tickmetrics = "true",
                            idsetup = "setup",
                            idgo = "go",
                            idfinal = NA_character_,
                            runtime = 50,
                            evalticks = seq(40,50),
                            metrics = c("count sheep", "count wolves", "count patches with [pcolor = green]"),
                            variables = list('initial-number-sheep' = list(values=c("\"LOW", "\"HIGH\"")),
                                             'initial-number-wolves' = list(values=c(50,150))),
                            constants = list("model-version" = "\"sheep-wolves-grass\"",
                                             "grass-regrowth-time" = 30,
                                             "sheep-gain-from-food" = 4,
                                             "wolf-gain-from-food" = 20,
                                             "sheep-reproduce" = 4,
                                             "wolf-reproduce" = 5,
                                             "show-energy?" = "false"))

nl@simdesign <- simdesign_simple(nl = nl, nseeds = 1)  ## works
nl@simdesign <- simdesign_ff(nl = nl, nseeds = 1)  ## Error "replacement has 1 row, data has 0" when calling run_nl_all()
nl@simdesign <- simdesign_distinct(nl = nl, nseeds = 1)  ## Error "replacement has 1 row, data has 0" when calling run_nl_all()

future::plan(multisession)

results <- run_nl_all(nl = nl, cleanup = "all")
nldoc commented 6 years ago

There is an escaped quote missing for your LOW variable in the variables list: list(values=c("\"LOW", "\"HIGH\"")) Adding the additional escaped quote did fix the problem on my machine: list(values=c("\"LOW\"", "\"HIGH\""))

And one additional note on why the simple simdesign worked. The simdesign_simple does not use any of the variable definitions. Instead, it only uses defined constants for creating a parameter table.

z3tt commented 6 years ago

Damn, I knew it would be something ridiculously simple... -.- Nevertheless, thank you very much! It is running as expected now!