How can I stop the monitor continually running? - netlogo

The monitor (below) is continually running and generating a random list of output, even though there is no tick activity.
Questions: Should it be continually running? Is there a way to monitor the list on the interface without the continual random output?
Code
to go
crt 100 [fd random 14 + 1]
end
to-report report-red-turtles
report [who] of turtles with [color = red]
end
To run:
On the interface, create a monitor report-red-turtles and a simple go button

It is by design that "Monitors automatically update several times per second". It's a convenient design in most cases, but can also have some weird consequences (be careful never to have side effects in monitor code!)
What happens in your case is that
[who] of turtles with [color = red]
produces different output each time it runs: the list produced by of is always in random order.
To get around this fact, you have two options.
Remove the randomness: sort [who] of turtles with [color = red].
Use a global variable (e.g. red-turtles), update it once per tick, and display that in your monitor.
It's a trade-off between simplicity and speed: the first option is simpler and cleaner, but more computationally expensive.

Related

Problem making a calculation in a monitor on the interface in Netlogo

I have a model that tracks energy levels in sheep, which I have defined as a breed. I have set up a monitor to calculate the mean energy level for the sheep, but need to consider what happens if there are no sheep at some point. I have tried numerous variations, the simplest of which is:
ifelse (any? sheep) ["NA"] [mean [energy] of sheep]
Unfortunately, I keep getting the error
Expected reporter.
I can work around this by creating a new global variable and reporter in the code, but this seems to be a bit of a waste. Am I doing something wrong or are there limitations on what kind of calculations can be done in a monitor on the Interface? If so, where are these limitations summarized?
Answer in three steps:
Difference between ifelse and ifelse-value
You are getting a syntax error there because a monitor expects a reporter, but ifelse is made to handle commands. The reporter version of ifelse is ifelse-value. If you just change ifelse to ifelse-value in your example, you see that you don't get any syntax error anymore. However, you will also see that if you do so and start your model with sheep having their energy, the monitor will show NA - see next point.
Correct use of any?
This happens because you are using any? the other way around. As you can see, any? reports true if the agentset is not empty. This means that the following reporter:
ifelse-value (any? sheep) ["NA"] [mean [energy] of sheep]
will report "NA" when there are sheep in the model, because that is the first reporter block.
Switch to:
ifelse-value (any? sheep) [mean [energy] of sheep] ["NA"]
and you have what you want. Just as in English: "If there are any sheep, do the calculation, else, this does not apply".
In any case, this does the job but it is superflous - see next point.
What monitors can do
Monitors are able to handle some of their reporters' runtime errors. You can simply put mean [energy] of sheep in your monitor and it will automatically show N/A when there are no sheep, without the need for you to handle the case.

keeping variable results after turtle dies netlogo

Looking for a way to store a turtle length of stay in the model after they have left the model. My model runs for several months and a few thousand turtles enter, undergo process then leave the area. It's complicate model (it's a hybrid DES and ABM) so I've tried to reproduce the simple bit below.
Turtles will be created at every tick and given a random length of stay but will only be able to begin process when they move to the right area (area-name) and when their time is up they leave the area. Their time-in-system reflects the wait for the area and the length-of-stay which I want to save once they're complete. If I leave them in the model it starts to break down after a couple of months and I suspect this is because the model has too many turtles still in the system for calculation and is inefficient.
go
create turtles 2
[
set time-in-system 0
set length-of-stay ceiling ((random-normal 48 4) + ticks)]
set shape "person"
if any? area-name with [not any? turtles-here]
[move-to one-of area-name]
]
undergo-process
end
to-undergo-process
ask turtles with [shape = "person"]
[
set time-in-system time-in-system + 1
]
ask turtles-on area-name
[if ticks = length-of-stay
[set shape "dot"
move-to exit-door]
end
I can then plot and see in realtime to make sure it is working
histogram time-in-system of turtles with [shape = "dot"]
but can't seem to figure out how to store them as unique values for plotting after the model has run and I have a dataset of outcomes without keeping them alive in the model. The real-time plot isn't necessary as long as I can store the unique values after they have left
If I ask them to die then I lose the unique values in the histogram. I don't want a tally of all values but each turtle's unique value at the end of the process after they left - at the moment the only solution I have to storing them is as an agent-set that stays alive in the exit-door patch but this takes up a lot of calculation power as the model progresses for months...
There may be a really simple command for this but I've been going round in circles through the programming manual trying to find it. Any tips appreciated
You should create a list storing the values of turtles that left.
Isolating only the code that is relevant for this purpose, it would be something like:
globals [
times
]
to setup
set times (list)
end
to leave-simulation ; This being executed by turtles.
set times lput (time-in-system times)
die
end
If your program is going to run for actual months, I recommend you use the file-write command to store your data. This way the data is preserved if the program halts for any reason; it gives you much more freedom to do the analysis you want without running the full simulation again.
If you write to a .csv (comma separated value) file, you can use almost any program (excel, R, matlab, python, C# or back to netlogo) to plot a histogram.

How to efficiently create data on one variable all agents have

I'm working with a NetLogo model on EV charging behaviour. All (500) agents monitor their my-charging-demand per tick and I want to find out what happens to this emergent behaviour when I change the policy intervention that is active (costs of electricity in this case). I am trying to show changes in charging characteristics such as charging-duration, charging power etc.
What is the best way to create data on the agents' my-charging-demand in time?
Right now I am plotting all their data in one graph using the following code:
ask adopters
[ create-temporary-plot-pen (word-who)
set-plot-pen-color color
plotxy ticks my-charging-demand
]
It works, but unfortunately it also made the model incredibly slow, as 500 pens are to be updated every tick. The model needs 105120 ticks before a whole year/run is completed, as each tick in the model represents 5 minutes. Therefore, speed does matter :-)
Is there a more efficient way to keep track / create data of one variable all agents have?
If I have understood this correctly, you want each agent to remember the value of its variable my-charging-demand across all time. If so, the easiest way (but I don't know if it's more efficient) is to have the list as a turtle variable. So, modify your turtles-own to add another variable:
adopters-own
[ ....
my-charging-demand
my-charging-demand-series
]
And wherever you have the code for calculating demand, add the result to the list
ask adopters
[ ...
set my-charging-demand ...
set my-charging-demand lput my-charging-demand my-charging-demand-series
...
]
I can't imagine a plot with 500 lines is readable. The plot should do something like the average of my-charging-demand or the proportion of turtles with my-charging-demand greater than some threshold.

how to report turtles state one tick before the simulation ends in Netlogo?

I've made a population model in Netlogo where the simulation stops when all my turtles have died OR the number of 300 ticks is reached. I need to report (or write to a file) the mean state of my turtles (turtle-own variables) one tick before the simulation ends. It would be easy if all simulations will run to 300 ticks, but in most cases the simulation ends before this happens (all turtles die). How can I achieve this? The death of the turtles is conditioned to either their "lifetime" runs out or to a stochastic probability of dying, so I can't predict when will this happen, and I need to know whether the last turtle died due to their lifetime running out or due to the probability worked against the turtle. Thanks!
Have you played around with BehaviorSpace at all? It works pretty well for means and sums etc. You can easily make BehaviorSpace experiments to export whatever reporters you set up to a .csv spreadsheet or table, whether you want reports at the end of your simulation or at each tick. For a simple example, if I want to know the mean x-coordinate of my turtles, I can set up the reporter using to-report:
to-report mean-xcor
let xlist ( [xcor] of turtles )
report mean xlist
end
Then, I can use Behavior Space (Tools > Behaviour Space) to set up an experiment that writes that mean xcor for all turtles at either each tick or only at the end of a run. The tool also allows you to set up multiple parameterizations of your simulation and compare results with different treatments- it's really handy! You can get creative with what you report in order to have the output be what you need. For your specific case, you could just make sure that your experiment is recorded at each tick.
You could also do this manually and with a little more control if you prefer. You can create a file and header during your setup using something like:
to setup-turtle-reporting
file-open "turtle_details_out.csv"
file-type (word "tick, who, xcor, ycor \n")
file-close
end
That sets up a .csv file in your model folder that has the column headers tick, who, xcor, and ycor. Then, during each tick you can have turtles write the appropriate variables to that same file:
to turtle-report
file-open "turtle_details_out.csv"
ask turtles [
file-type (word ticks ", " who ", " xcor ", " ycor "\n" )
]
file-close
end
This option gives you a bit more control in some ways, but is fiddlier. You will have to also play around with file-delete or manually delete/rename the file as you complete different simulations, as file-type will append to the existing file rather than overwriting it.

How to randomly place turtles at each model opening?

Every time that I open my Netlogo model, the created turtles are placed at the same place. I have 1000 simulations and I use the behaviorSpace. I tried random-seed but how can I use this function without writing, for each simulation in the behaviorSpace:
random-seed 0
create-turtles
random-seed 1
create-turtles
random-seed 2
create-turtles
....
random-seed 1000
create-turtles
?
Update
I don't use behaviorSpace to repeat simultaneously 1000 times my model but I open 1000 times my file .nlogo. I would like to find a way to have locations of turtles that are different at each file opening (I used one-of to place turtles in patches).
Thank you very much for your help.
(UPDATED)
In your comment, you supply the crucial information that you are using import-world. This restores the exact state of the entire world, including the state of the random number generator! As a result, you get the same model run every time afterwards.
If you want to re-seed the random number generator so you get a different run each time, then, after import-world, say random-seed new-seed.
random-seed behaviorspace-run-number