📄 ---crowds.nlogo
字号:
; re-implementation of; ; Wander Jager, Roel Popping and Hans van de Sande (2001) ; Clustering and Fighting in Two-party Crowds: Simulating the Approach-avoidance Conflict ; Journal of Artificial Societies and Social Simulation vol. 4, no. 3, ; <http://www.soc.surrey.ac.uk/JASSS/4/3/7.html> ;; Nigel Gilbert; 30 August 2003;; for NetLogo 1.3 <http://ccl.northwestern.edu/netlogo/>;globals [ step ; steps completed (= the simulated time in seconds) ] breeds [ people ] people-own [ acquaintances ; list of 15 people of my party with whom I am acquainted visible-people ; list of all the people that I saw as a result of my last scan number-of-visible-own-party ; number of people of my own party among the visible people number-of-visible-other-party ; number of people of the other party among the visible people quad-own-party ; the quadrant containing the most people of my (the other ... quad-other-party ; party). A heading (45, 135, 225, 315) or zero if no one. aggression ; my aggression motivation score (0 .. 30) party ; my party (red or green) kind ; whether a hardcore, hanger-on or bystander fighting ; number of steps until I stop fighting (0 if I am not fighting) defending ; number of steps until I stop defending myself (or 0 if I am not) ] ; create the agents and give them their initial attributes, acquaintances, location, etc. to setup locals [number-of-hardcore number-of-hangers-on number-of-bystanders ] clear-all ask patches [ set pcolor white ] set number-of-hardcore (population * hardcore-percent / 100) ;hardcore-percent set by slider set number-of-hangers-on (2 * number-of-hardcore) set number-of-bystanders (population - number-of-hardcore - number-of-hangers-on) create-custom-people population [ ifelse who < number-of-hardcore [ set kind "hardcore" ] [ ifelse who < number-of-hardcore + number-of-hangers-on [ set kind "hangers-on" ] [ set kind "bystander" ] ] ifelse asymetrical [ ifelse who mod 4 = 0 [ set party "red" ] [ set party "green" ] ] [ ifelse who mod 2 = 0 [ set party "red" ] [ set party "green" ] ] set-party-color set shape "circle" ; distribute the agents at random over the grid setxy ((random-int-or-float screen-size-x) - screen-edge-x) ((random-int-or-float screen-size-y) - screen-edge-y) set aggression 0 set acquaintances [] set fighting 0 set defending 0 ] ask people [ make-friends scan ]end; give the agent 15 acquaintances, chosen at random from those of my party.; Acquaintances are bi-directional. I may already have some, placed here by; my friends when they made bi-links, so now I must just make up the number to 15to make-friends locals [ number-to-choose my-party-people friend ] without-interruption [ set number-to-choose 15 - length acquaintances set my-party-people people with [ (party = party-of myself) and (self != myself) ] repeat number-to-choose [ set friend random-one-of my-party-people with [ not member? myself acquaintances ] set acquaintances fput friend acquaintances ; tell my friend that I am its friend set acquaintances-of friend fput self acquaintances-of friend ] ]end; set the display colour of the turtle to my party colourto set-party-color ifelse party = "red" [ set color red ] [ set color green ]end; repeatedly executed when the user clicks the 'go' button; Run 5400 steps and then stop; For each agent, the process is to look (scan), think (adjust aggression motivation) and act (according to the; behaviour model) again and againto go set step step + 1 if step > 5400 [ stop ] ask people [ do-one-step ] do-plots end; top level process for each agentto do-one-step ifelse fighting > 0 or defending > 0 ; either fight (or defend) or scan and behave [ fight ] [ if time-to-scan [ scan adjust-aggression ] behave ]end; report true if this agent should scan the locality this time stepto-report time-to-scan report (kind = "hardcore") or (kind = "hanger-on" and step mod 2 = 0) or (kind = "bystander" and step mod 8 = 0) end; a fight lasts for 100 steps. Reduce the fight timers by 1, and if the fight has ended; set the aggressor's aggression to zero. to fight if fighting > 0 [ set fighting fighting - 1 if fighting = 0 [ set aggression 0 ] ] if defending > 0 [ set defending defending - 1 ]end; adjust the aggression motivation according to how many people of my own and the other; party I can see.to adjust-aggression set number-of-visible-own-party count visible-people with [ party = party-of myself ] set number-of-visible-other-party count visible-people with [party != party-of myself ] ifelse number-of-visible-own-party > number-of-visible-other-party + 10 [ set aggression aggression + 1] [ if number-of-visible-other-party > number-of-visible-own-party + 10 [ set aggression aggression - 1] ] ifelse aggression < 0 [set aggression 0] [if aggression > 30 [ set aggression 30 ] ]end ; this is the behaviour model.; Choose different actions according to my level of aggression and whether there is anyone in the; next door cell that I could fightto behave locals [ opponent acquaintance ] ifelse aggression > 15 [ set color 2 ; approach state set opponent in-direct-contact ifelse opponent != nobody and aggression > 25 ; aggressive state [ start-fighting opponent ] [ ifelse quad-other-party > 0 [ move-to-other-party ] [ behave-with-standard-rule ] ] ] [ set-party-color ; avoidance state ifelse number-of-visible-other-party - number-of-visible-own-party > 10 [ behave-with-standard-rule ] [ set acquaintance see-acquaintance ifelse acquaintance != nobody [ approach-acquaintance acquaintance ] [ ifelse quad-own-party > 0 [ move-to-own-party ] [ behave-with-standard-rule] ] ] ]end; fight for 100 steps. Fighting people are coloured blackto start-fighting [ opponent ] set fighting 100 set color black set defending-of opponent 100 set color-of opponent blackend; an agent is in direct contact with another if they are in adjacent cells; report an agent of the other party who is an adjacent cell, or nobody if; there is none, or one at random if there is more than one to-report in-direct-contact report random-one-of (in-moore-range people 1) with [party != party-of myself] end; the behaviour model for when the agent is not aggressive or approachingto behave-with-standard-rule locals [ random-number ] set random-number (random 100) ifelse random-number < 50 [ move-randomly ] [ ifelse random-number < 95 [ move-in-locality ] [ stand-still ] ]end; report a randomly chosen one of my acquaintances from all those that I can see ; (i.e. located within a 40 unit square centred on me)to-report see-acquaintance locals [ visible-acquaintances ] set visible-acquaintances filter [abs (pxcor - pxcor-of ?) <= 20 and abs (pycor - pycor-of ?) <= 20] acquaintances ifelse empty? visible-acquaintances [ report nobody ] [ report item (random length visible-acquaintances) visible-acquaintances ]end; move towards the acquaintanceto approach-acquaintance [acquaintance ] set heading towards-nowrap acquaintance moveend; move one unit in a diagonal direction to the quadrant that has most members of my partyto move-to-own-party set heading quad-own-party move end ; move one unit in a diagonal direction to the quadrant that has most members of the other partyto move-to-other-party set heading quad-other-party move end ; move one unit on a random directionto move-randomly set heading (random-int-or-float 360) moveend; move one unit turning left first. If repeated, this will yield a circular pathto move-in-locality left 90 moveend; move one unit in the direction I am heading. If that would bump me into the edge, do an about-turn; (180 degrees) first; If the move would mean going into a patch that is already occupied, don't move after all.; Then ensure that I am in the middle of my patchto move if (xcor + dx < 0 - screen-edge-x) or (xcor + dx > screen-edge-x) or (ycor + dy < 0 - screen-edge-y) or (ycor + dy > screen-edge-y) [ set heading heading + 180 ] if not any? people-at dx dy [ forward 1 ] centreendto stand-still ; do nothingend; see how many people I can see, looking in the 40 x 40 Moore neighbourhood around me; Then see in which quadrant there are the most of my own and the other partiesto scan set visible-people in-moore-range people 20 set quad-own-party quad party ifelse party = "red" [ set quad-other-party quad "green" ] [ set quad-other-party quad "red" ]end; report the quadrant in which there are the most members of the-party; The number returned is either the direction of a diagonal through the quadrant; (45, 135, 225 or 315) or 0, the latter meaning that there are no people of; that party visible anywhereto-report quad [ the-party ] locals [ quad1 quad2 quad3 quad4 quad-max ] set quad1 count visible-people with [ party = the-party and xcor >= xcor-of myself and ycor >= ycor-of myself] set quad2 count visible-people with [ party = the-party and xcor >= xcor-of myself and ycor <= ycor-of myself] set quad3 count visible-people with [ party = the-party and xcor <= xcor-of myself and ycor <= ycor-of myself] set quad4 count visible-people with [ party = the-party and xcor <= xcor-of myself and ycor >= ycor-of myself] set quad-max max (list quad1 quad2 quad3 quad4 ) if quad-max = 0 [ report 0 ] ifelse quad1 = quad-max [ report 45 ] [ ifelse quad2 = quad-max [ report 135 ] [ ifelse quad3 = quad-max [ report 225 ] [ report 315 ] ] ]end; move to the centre of the patch that I occupy at the momentto centre setxy pxcor-of patch-here pycor-of patch-hereend; report an agentset of the agents that are inside the Moore neighbourhood of dimension 2nto-report in-moore-range [agents n] report agents with [abs (pxcor - pxcor-of myself) <= n and abs (pycor - pycor-of myself) <= n] end; add the results from a step to the plotsto do-plots set-current-plot "Clusters with own party" plot mean values-from people [ count in-moore-range people with [ party = party-of myself ] 3 ]end; end of program@#$#@#$#@GRAPHICS-WINDOW3911981346251514.01101110CC-WINDOW5507822602Command CenterSLIDER3182203115populationpopulation040040011peopleSLIDER35134207167hardcore-percenthardcore-percent0551
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -