1. State Space
Let the grid size be S = 50. Cells are indexed by
i = 1, ..., N with N = S^2 = 2500, and each cell has coordinates
(x_i, y_i).
d_ij = sqrt((x_i - x_j)^2 + (y_i - y_j)^2)
The matrix D = (d_ij) is fully precomputed and used by all endogenous spatial interaction terms.
2. Amenity Surface
The amenity field is exogenous after initialization. For each cell i, the raw amenity level is
A~_i = 0.65 exp(-((x_i-c)^2 + (y_i-c)^2)/260)
+ 0.45 exp(-(x_i-0.62S)^2/42) (0.3 + 0.7 y_i/(S-1))
+ 0.2 exp(-(x_i-y_i-8)^2/60) + eps_i
where c = (S-1)/2 and eps_i is a seeded pseudo-random draw on [0, 0.28).
The final amenity index is min-max normalized:
A_i = (A~_i - min_k A~_k) / (max_k A~_k - min_k A~_k)
3. Initial Population Share
The initial population distribution is centered and tilted toward amenity-rich cells. Define
r_i = sqrt((x_i-c)^2 + (y_i-c)^2)
x~_i(0) = 0.25 + exp(-r_i^2/420) + 0.35 A_i
x_i(0) = x~_i(0) / sum_k x~_k(0)
Hence x_i(t) >= 0 and sum_i x_i(t) = 1 for all periods.
4. Utility Components
At each step, utility is evaluated from the current population share vector x(t).
The implemented endogenous terms are
Access_i(x) = sum_j x_j exp(-tau d_ij)
Crowd_i(x) = sum_j x_j / (1 + d_ij)
where tau is the slider named Travel Cost.
The scalar utility of choosing cell i is
U_i(x) = a A_i + g Access_i(x) - c Crowd_i(x)
with a = Amenity Weight, g = Agglomeration,
and c = Congestion.
5. Logit Choice and Dynamic Update
The simulator uses a multinomial logit map with fixed inverse-noise parameter
lambda = 10:
P_i(x) = exp(lambda U_i(x)) / sum_k exp(lambda U_k(x))
The population share then follows the discrete-time partial adjustment dynamic
x_i(t+1) = (1-rho) x_i(t) + rho P_i(x(t))
where rho is the slider Relocation Share. This is exactly the interpretation that, in each period,
only a fixed small share of the population is allowed to relocate while the remainder stays put.
6. Visualization and Run Logic
The three heatmaps display the normalized amenity field A, the current population share
x(t), and the current logit choice vector P(x(t)).
The Start button advances the system repeatedly and automatically stops after
100 steps in the current implementation. The Step button advances the model by one
additional step regardless of whether the auto-run cap has already been reached.