Skip to content
Snippets Groups Projects
Commit 61505db6 authored by xo30xoqa's avatar xo30xoqa
Browse files

Non-breeding skylarks only look once for a neighbour to follow

parent fc239eaa
No related branches found
No related tags found
No related merge requests found
......@@ -36,27 +36,25 @@
Ecology and Evolution, 12(1), e8461. https://doi.org/10.1002/ece3.8461
"""
@species Skylark begin
# species parameters
const movementrange::Length = 500m #XXX arbitrary
const visionrange::Length = 200m #XXX arbitrary
## SPECIES PARAMETERS
# juveniles
const eggtime::Int64 = 11 # days from laying to hatching
const nestlingtime::Int64 = 9 # days from hatching to leaving nest
const fledglingtime::Int64 = 21 # days from leaving the nest to independence
#XXX predation mortality should be habitat-dependent
const eggpredationmortality::Float64 = 0.03 # per-day egg mortality from predation
const nestlingpredationmortality::Float64 = 0.03 # per-day nestling mortality from predation
const fledglingpredationmortality::Float64 = 0.01 # per-day fledgling mortality from predation
const firstyearmortality::Float64 = 0.38 # total mortality in the first year after independence
# skylarks migrate from autumn to early spring, with the females leaving earlier
# and arriving later than the males
# migration
const migrationdeparture::Tuple{AnnualDate,AnnualDate} = ((September, 15), (November, 1))
const migrationarrival::Tuple{AnnualDate,AnnualDate} = ((February, 15), (March, 1))
const migrationdelayfemales::Day = Day(15)
const migrationmortality::Float64 = 0.33 # chance of dying during the winter
# habitat requirements
const minimumterritory = 5000 # size of territory under ideal conditions
const mindistancetoedge = 60m # minimum distance of habitat to vertical structures
const maxforageheight = 50cm # maximum preferred vegetation height for foraging
......@@ -64,20 +62,26 @@
const nestingheight = (15cm, 25cm) # min and max preferred vegetation height for nesting
const nestingcover = (0.2, 0.5) # min and max preferred vegetation cover for nesting
# breeding
const matefaithfulness = 0.5 # chance of a female retaining her previous partner
const nestingbegin::Tuple{AnnualDate,AnnualDate} = ((April, 10), (April, 20)) # begin nesting in the middle of April
const nestbuildingtime::UnitRange{Int64} = 4:5 # 4-5 days needed to build a nest (doubled for first nest)
const eggsperclutch::UnitRange{Int64} = 2:5 # eggs laid per clutch
const nestingend::AnnualDate = (August, 15) # end of the nesting period
# individual variables
# mating / non-breeding
const movementrange::Length = 500m #XXX arbitrary
const visionrange::Length = 200m #XXX arbitrary
const flockingdistance::Length = 30m #XXX arbitrary
## INDIVIDUAL VARIABLES
timer::Int64 = 0 # a counter that can be used for different purposes
firstnest::AnnualDate = (April, 15) # is redefined by each individual in @create(Skylark)
migrationdates::Tuple = () # is defined by each individual in @create(Skylark)
mate::Int64 = -1 # the agent ID of the mate (-1 if none)
nest::Tuple = () # coordinates of current nest
clutch::Int64 = 0 # number and life stage of offspring in current clutch
#following::Int64 = -1 # ID of the individual being followed in the non-breeding phase
following::Int64 = -1 # ID of the individual being followed in the non-breeding phase
end
......@@ -89,26 +93,27 @@ end
Non-breeding adults move around with other individuals and check for migration.
"""
@phase Skylark nonbreeding begin
#FIXME searching for neighbours is *the* performance bottleneck!!
# Two options:
# (a) ignore flocking, simply move randomly (scientifically OK, doesn't look as good)
# (b) select a random neighbour once, then keep following that individual
# flocking behaviour - follow a random neighbour or move randomly
neighbours = ()
#neighbours = @neighbours(self.visionrange) #XXX check for the closest neighbour(s)?
isempty(neighbours) ?
@walk("random", self.movementrange) :
@follow(@rand(neighbours), 30m) #XXX magic number
# check if the bird migrates
arrive, depart = self.migrationdates
if model.date >= depart
if model.date >= self.migrationdates[2]
@kill(self.migrationmortality, "migration")
self.sex == male ?
@setphase(territorysearch) :
@setphase(matesearch)
@migrate(arrive)
@migrate(self.migrationdates[1])
return
end
# flocking behaviour - follow a neighbour or move randomly
self.following > 0 && isnothing(@animal(self.following)) && (self.following = -1)
if self.following == -1
neighbours = @neighbours(self.visionrange)
if isempty(neighbours)
@walk("random", self.movementrange)
return
else
self.following = @rand(neighbours).id
end
end
@follow(@animal(self.following), self.flockingdistance)
end
"""
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment