I am creating a simulation which copies shoplifter behaviour. Turtles are split between "professional" and "novice" shoplifters and if "professionals" are apprehended by store security they might (1/2) want to select a new store to target "new-store-required".
"professional" shoplifters target the store with the lowest "security" value in a certain radius, all values are set as they are created.
I am trying to set a new "target-store", a "store" in-radius 10 with the second lowest "security", i.e. excluding the current "target-store" but I am having difficulty.
So far I have attempted to made several additions to the following code to exclude the current target store, this includes variations of "member? my patches" as the "store" where the shoplifter has been apprehended is added to this "patch-set" which will inform a later command. Also I have made a list of ascending "security" values to tell the "shoplifter" to target the "store" with "security" (the value which determines store vulnerability) the same as item 1 on the list, but I fear this might not work because their original target-store might not necessarily be item 0 as they target the store with the lowest "security" in a 10 unit radius.
These are the lines of code I am working with at the moment, any suggestions would be greatly appreciated.
***Edit: I could ideally like the code to make use of "mypatches" so each time a professional shoplifter is apprehended at a store that store can be added to mypatches and the subsequent target-store can exclude all stores which are members of mypatches.
to new-target-store
ask turtles [ if
new-store-required = 1 and professional = 1 and (random-float 1 < 0.5) [
set target-store min-one-of store in-radius 10 [security]
]
]
end
Edit 2: I've fixed what was wrong.
You may want to include your setup
code, or a stripped-down version of it if it's really long, to make sure that answers conform to the structure you've used. I would approach this by having a turtles-own
variable to store their current target, which they can try to fill if it is empty (rather than using an extra boolean for that purpose). Also, you may want to convert your 1/0 options to true
/false
for cleaner code. Check out this example setup:
globals [ stores ]
patches-own [ security ]
turtles-own [
current-target
professional?
mypatches
]
to setup
ca
ask n-of 20 patches [
set pcolor green
set security 1 + random 10
]
set stores patches with [ pcolor = green ]
crt 5 [
setxy random-xcor random-ycor
pd
set professional? one-of [ true false ]
set current-target nobody
set mypatches ( patch-set )
]
reset-ticks
end
This sets up a world with some green patches that are grouped into the patch-set
called stores
. Also, you have some turtles that have the boolean professional?
set to either true or false. They initialize with no current-target
store, and an empty mypatches
patch-set
variable.
Now, you can have turtles check if their current-target
exists. If it does not, they can assign a store to that variable from the set of stores (possible-targets
, here) that are not equal to the patch-here
of the asking turtle. Professional thieves can further refine possible-targets
to exclude any stores at which they have been apprehended, by excluding any stores that are a member of their mypatches
patch-set
variable. More details in comments:
to go
ask turtles [
; if you have no target currently
if current-target = nobody [
; Create a temporary patch set made up of all stores except for
; the one that I'm currently in
let possible-targets stores with [ self != [patch-here] of myself ]
ifelse professional? [
; Have professional thieves revise their possible targets to exclude
; any in the patchset mypatches, then choose a possible target
set possible-targets possible-targets with [ not member? self [mypatches] of myself ]
set current-target min-one-of possible-targets in-radius 10 [ security ]
] [
; Have amateur thieves choose randomly from the possible targets
set current-target one-of possible-targets
]
]
; move closer to your current target, or
; move to it exactly if you're near enough
ifelse current-target != nobody [
face current-target
ifelse distance current-target > 1 [
fd 1
] [
move-to current-target
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; *** do your shoplifting attempt/check here ***
; For this example, just have professional thieves sometimes
; add this patch to their mypatches patchset
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
if professional? and random-float 1 < 0.5 [
set mypatches ( patch-set mypatches patch-here )
]
; Reset current-target to nobody
set current-target nobody
]
] [
; if no suitable nearby targets, wander randomly
rt random 61 - 30
fd 1
]
]
tick
end
If you run that long enough, eventually your professional thieves will stop being able to find target stores as they have added all stores to their mypatches
variable.