NetLogo: How to build using the "with" syntax in the "ifelse" syntax with specific conditions? - netlogo

How can I build a syntax for an "ifelse" statement that has a turtle in a specified patch and has the turtle determine if the turtle's color is the specified color? The following is sample code, but it won't work. Incidentally, I would like to build it using "max-pxcor - 1".
ifelse count turtles-on patch (max-pxcor - 1) with [color = red] = 1[ ;The following code is omitted

(1) The patch X Y notation selects a specific patch but you have not provided a pycor. I assume you therefore want any patch with the correct value for pxcor. How many of those patches are coloured red? (2) If you are not selecting a patch with its identifier, then you are working with a patchset rather than a patch, even if there is only one patch in that set. If you need to get a patch from a patchset, you need one-of.
If you actually want to identify that patch so you can do something with it, then this approach separates the patches from the turtles so is reasonably readable:
let wanted-patch one-of patches with [pxcor = max-pxcor - 1 and color = red]
ifelse count turtles-on wanted-patch = 1
[
But you could also do:
ifelse any? patches with [pxcor = max-pxcor - 1 and
color = red and
count turtles-here = 1]
[
Of, if you genuinely want the patchset so the total number of turtles on all the right hand column red patches is 1 (so 1 on one patch and 0 on others), then:
ifelse count (turtles-on patches with [pxcor = max-pxcor - 1 and color = red]) = 1
[
For this last one, the () are optional, for readability.

Related

How to select patches based on the same variable value in Netlogo

When one variable of a patch reaches a certain value (e.g. age = 75 ), I redirect the patch to another procedure (called retirement) where I want to select all the patches that share the same value of the variable Farm_ID so the procedure is applied to all the patches.
I'm looking for a command which mean "the same as", I also considered to use the to-report and report procedure to report the pxcor and pycor of the original patch and then ask the other patches with the same ID_Farm as the patch pxcor pycor
But I feel like I'm missing something in the essence of using Netlogo (I'm a newbie).
to start-simulation
reset-timer
tick-advance 70
;; increase the farmer's age
ask patches with [seed = 1] [set age age + 1]
ask patches [
if age = 75 [ retirement ]
]
;; other stuffs
end
to retirement
ask patches with [ ID_Farm = ???]
;; procedure to change the variable ID_Farm depending on the closest patches with a different ID_Farm
end
You need myself (see here), and more specifically you need to use variable = [variable] of myself.
See a minimal and reproducible example below:
to setup
clear-all
ask patches [
ifelse (pxcor > 0)
[set pcolor lime]
[set pcolor orange]
]
end
to go
ask one-of patches [
type "I am the chosen patch. My color is " type (ifelse-value (pcolor = 25) ["orange"] (pcolor = 65) ["lime"] ["cyan"]) print ". I and all patches having my same color will become cyan."
operate-on-patches-with-my-same-color
]
end
to operate-on-patches-with-my-same-color
ask patches with [pcolor = [pcolor] of myself] [
set pcolor cyan
]
end
When you check the myself entry in the NetLogo Dictionary, note the difference between self and myself. At the beginning it may be confusing, but as you get more and more used with how NetLogo works it will become clear.

Divide regions accordingly to physical features

I'm working on a smaller project and got stuck on an issue, I'm not really sure if it's possible to solve it in NetLogo but I want to give StackOverflow a go!
I got a model that divides the world into different parts and randomly add physical features (such as rivers). If a feature goes through the whole region, I want it to separate the region and make into two regions. As an example, in the picture below, I want to separate the purple region into two unique regions accordingly to the physical feature (black).
The code I used to generate the picture above, can be found below.
to setup
ca
;Setting world.
resize-world 0 19 0 19
;Creating regions.
let x 5
let y 5
let col 45
while [y <= max-pycor + 1][
while [x <= max-pxcor + 1 ][
ask patches with [pxcor < x and pxcor >= x - 5 and pycor < y and pycor >= y - 5][
set pcolor col
]
set x x + 5
set col col + 10
]
set x 5
set y y + 5
]
;Generating physical features.
ask n-of 5 patches[ sprout 1[
set pcolor black]
]
let i 0
while [ i < (max-pycor * 2 )][
ask turtles [
fd 1
set pcolor black
ifelse (random 20 <= 1)
[
rt one-of [-90 0 90]
forward 1
]
[
fd 1
set pcolor black
fd 1
set pcolor black
]
set pcolor black
set i i + 1]
]
ask turtles [die]
end
My strategy for handling this is to realize that all we really need to do is "flood" a patch out by color and tag all the found adjacent patches, then repeat for any un-tagged, non-black patches until they are all done.
NetLogo does not have a "flood" command to get all patches adjacent to a patch meeting a criteria, so we make a special reporter of our own to handle it, patches-adjacent. Then it's just easy to ask those patches-adjacent to set their region to the currently chosen region.
I don't love this code, it's a little finicky and would be prone to infinite loops if tweaked incorrectly, but it should work. I bet there is a cleaner way to do this that I'm not thinking of at the moment.
; add a variable to track the different regions
; the default value will be `0` for each patch when `clear-all` is called
patches-own [ region ]
to set-regions
let current-region 1
; only act on non-black patches that haven't yet been assigned a region
let untagged patches with [ region = 0 and pcolor != black ]
while [any? untagged] [
ask one-of untagged [
ask patches-adjacent [
set region current-region
]
]
; update the region and the untagged patches we have left to process
set current-region current-region + 1
set untagged patches with [ region = 0 and pcolor != black ]
]
; this is just to get a view of the regions to quickly see if our code worked, it can be removed
ask patches [ set plabel region ]
end
to-report patches-adjacent
report patches-adjacent-ex (patch-set self) pcolor
end
to-report patches-adjacent-ex [found pc]
let newly-found neighbors4 with [ (not member? self found) and pcolor = pc and region = 0 and pcolor != black ]
set found (patch-set found newly-found)
ask newly-found [
; use recursion to find the patches adjacent to each newly-found one
; relying on updating the `found` agentset as we go to avoid duplicates
; or looping forwarder
set found (patches-adjacent-ex found pc)
]
report found
end
I solved this by using the Patch Clusters model that can be found in the NetLogo model library.

Netlogo - how to count turtles number around a specific turtle

I need to "do-something-special" if around yellow turtle there is at least 3 blue turtles . Is the code bellow correct?
I tried
ask turtles with [color = yellow]
[
if count turtles in-radius 1 with [color = blue] >= 3
[do-something-special]
]
do-something-special should remove (disappear) 3 of blue turtles and current yellow one
Did I do the location of relevant turtles correctly and how do I kill them after I find them?
Hannah's answer is good but the linked example won't fully fix your problem. Since you will be using the set of close agents twice (once to count and once to potentially remove some), you should also create an agentset for efficiency reasons (you don't want to create it twice). Here is a full solution.
ask turtles with [color = yellow]
[ let near-blue turtles in-radius 1 with [color = blue]
if count near-blue >= 3
[ ask n-of 3 near-blue [die]
die
]
]
Also, if you don't care about the exactness of the radius, an alternative to turtles in-radius 1 would be turtles-on (patch-set neighbors patch-here), which is all the turtles on the neighbouring and same patches to wherever your asker turtle is sitting.
At the moment your code counts the amount of turtles that are blue in the radius of one patch around the yellow turtle. If the amount of blue turtles is bigger/equal 3 the yellow turtles die if you use the "die" command instead of "do-something-special". So it looks as follows.
ask turtles with [color = yellow]
[
if count turtles in-radius 1 with [color = blue] >= 3
[die]
]
Maybe you can merge the code with the following example and then kill the neighbors.

NetLogo: select a patch with neighbors having certain qualities?

I want to let my turtle move to certain patch and make a "splotch". The central patch = my turtle location, can be selected randomly, however satisfy two conditions:
has to be in a certain distance from turtle's actual position
has to surrounded (neighbors in certain radius) by patches with specific quality
The reason is to create kind of "buffers" around my turtle's position, with aim to obstruct the close proximity of my clumps.
Please, how can I satisfy these two conditions?
As far, I have:
to go
ask turtles [
; select one of patches in specific distance, and
; surrounded by patches with no magenta color
let aaa one-of patches with [distance myself > 3 and
all? neighbors with [pcolor != magenta]]
; how to write this condition above ??
; and how replace "neighbors" by "in-radius"??
move-to aaa
ask neighbors [ ; create clump of magenta patches
set pcolor magenta ]
ask patch-here [ ; set central patch to magenta
set pcolor magenta ]
]
You're almost there; you just need to reread the documentation for all? and any?.
let _candidates patches with [distance myself > 3]
set _candidates _candidates with [
not any? (patches in-radius 3 with [pcolor = magenta])
]
let aaa one-of _candidates
If it is possible that there will be no candidates, you should guard against that.

How can I make a turtle randomly choose one of two conditions?

I have the code :
if color of patch-here = blue [set heading towards one-of patches in-radius 180 with pcolor = grey ( do that or ) die ]
What I want to be able to do is to allow each turtle to randomly select one of the two options. I appreciate I could assign each command a number and then use a random number generator to select one of the two commands, but I am wondering whether there is a combination of commands that I could use to replace ( do that or ).
Thanks.
Roll a dice, if dice < 5, do something, else do the other thing. Example:
if pcolor = blue [
let dice random 10
ifelse dice < 5 [
set heading towards one-of patches in-radius 180 with pcolor = grey]
[die]
]