Skip to content

Commit bde1251

Browse files
TortarDatseris
andauthored
Update multiagent vs. union performance docs for Julia 1.11 (#1091)
* Update multiagent vs. union performance docs for Julia 1.11 * Update performance_tips.md * Update performance_tips.md * Update performance_tips.md * Update multiagent_vs_union.jl * Update performance_tips.md * Update performance_tips.md * Update Project.toml * Update Project.toml --------- Co-authored-by: George Datseris <[email protected]>
1 parent b7d6824 commit bde1251

File tree

3 files changed

+29
-25
lines changed

3 files changed

+29
-25
lines changed

Project.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
name = "Agents"
22
uuid = "46ada45e-f475-11e8-01d0-f70cc89e6671"
33
authors = ["George Datseris", "Tim DuBois", "Aayush Sabharwal", "Ali Vahdati", "Adriano Meligrana"]
4-
version = "6.1.11"
4+
version = "6.1.12"
55

66
[deps]
77
CSV = "336ed68f-0bac-5ca0-87d4-7b16caf5d00b"

docs/src/performance_tips.md

Lines changed: 5 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -134,12 +134,7 @@ t = joinpath(dirname(dirname(x)), "test", "performance", "variable_agent_types_s
134134
include(t)
135135
```
136136

137-
We see that Unions of up to three different Agent types do not suffer much.
138-
Hence, if you have less than four agent types in your model, using different types is still a valid option.
139-
For more agent types however we recommend using the [`@multiagent`](@ref) macro.
140-
141-
Finally, we also have a more realistic benchmark of the two approaches at `test/performance/multiagent_vs_union.jl` where the
142-
result of running the model with the two methodologies are
137+
Finally, we also have a more realistic benchmark of the two approaches at [`test/performance/multiagent_vs_union.jl`](https://github.com/JuliaDynamics/Agents.jl/blob/main/test/performance/multiagent_vs_union.jl) where each type has a different set of behaviours, unlike in the previous benchmark. The result of running the model with the two methodologies are
143138

144139
```@example performance_2
145140
using Agents
@@ -148,7 +143,8 @@ t = joinpath(dirname(dirname(x)), "test", "performance", "multiagent_vs_union.jl
148143
include(t)
149144
```
150145

151-
In reality, we benchmarked the models also in Julia>=1.11 and from that version on a `Union` is considerably
152-
more performant. Though, there is still a general 1.5-2x advantage in many cases in favour of [`@multiagent`](@ref),
153-
so we suggest to use [`@multiagent`](@ref) only when the speed of the multi-agent simulation is really critical.
146+
As you can see, [`@multiagent`](@ref) has the edge over a `Union`: there is a general 1.5-2x advantage in many cases
147+
in its favour. This is true for Julia>=1.11, where we then suggest to go with [`@multiagent`](@ref) only if the speed of the
148+
simulation is critical. However, keep in mind that on Julia<=1.10 the difference is much bigger: [`@multiagent`](@ref)
149+
is almost one order of magnitude faster than a `Union`.
154150

test/performance/multiagent_vs_union.jl

Lines changed: 23 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -62,11 +62,15 @@ function agent_step!(agent::GridAgentFour, model1)
6262
agent.one += sum(a.one for a in nearby_agents(agent, model1))
6363
end
6464
function agent_step!(agent::GridAgentFive, model1)
65-
targets = filter!(a->a.one > 1.0, collect(types, nearby_agents(agent, model1, 3)))
65+
targets = Iterators.filter(a->a.one > 1.0, nearby_agents(agent, model1, 3))
6666
if !isempty(targets)
67-
idx = argmax(map(t->euclidean_distance(agent, t, model1), targets))
68-
farthest = targets[idx]
69-
walk!(agent, sign.(farthest.pos .- agent.pos), model1)
67+
farthest = 0.0
68+
a = first(targets)
69+
for t in targets
70+
d = euclidean_distance(agent, t, model1)
71+
d > farthest && (a, farthest = t, d)
72+
end
73+
walk!(agent, sign.(a.pos .- agent.pos), model1)
7074
end
7175
end
7276
function agent_step!(agent::GridAgentSix, model1)
@@ -93,31 +97,35 @@ end
9397

9498
################### DEFINITION 2 ###############
9599

96-
@inline agent_step!(agent, model2) = agent_step!(agent, model2, variant(agent))
100+
agent_step!(agent, model2) = agent_step!(agent, model2, variant(agent))
97101

98-
@inline agent_step!(agent, model2, ::GridAgentOne) = randomwalk!(agent, model2)
99-
@inline function agent_step!(agent, model2, ::GridAgentTwo)
102+
agent_step!(agent, model2, ::GridAgentOne) = randomwalk!(agent, model2)
103+
function agent_step!(agent, model2, ::GridAgentTwo)
100104
agent.one += rand(abmrng(model2))
101105
agent.two = rand(abmrng(model2), Bool)
102106
end
103-
@inline function agent_step!(agent, model2, ::GridAgentThree)
107+
function agent_step!(agent, model2, ::GridAgentThree)
104108
if any(a-> variant(a) isa GridAgentTwo, nearby_agents(agent, model2))
105109
agent.two = true
106110
randomwalk!(agent, model2)
107111
end
108112
end
109-
@inline function agent_step!(agent, model2, ::GridAgentFour)
113+
function agent_step!(agent, model2, ::GridAgentFour)
110114
agent.one += sum(a.one for a in nearby_agents(agent, model2))
111115
end
112-
@inline function agent_step!(agent, model2, ::GridAgentFive)
113-
targets = filter!(a->a.one > 1.0, collect(GridAgentAll, nearby_agents(agent, model2, 3)))
116+
function agent_step!(agent, model2, ::GridAgentFive)
117+
targets = Iterators.filter(a->a.one > 1.0, nearby_agents(agent, model2, 3))
114118
if !isempty(targets)
115-
idx = argmax(map(t->euclidean_distance(agent, t, model2), targets))
116-
farthest = targets[idx]
117-
walk!(agent, sign.(farthest.pos .- agent.pos), model2)
119+
farthest = 0.0
120+
a = first(targets)
121+
for t in targets
122+
d = euclidean_distance(agent, t, model2)
123+
d > farthest && (a, farthest = t, d)
124+
end
125+
walk!(agent, sign.(a.pos .- agent.pos), model2)
118126
end
119127
end
120-
@inline function agent_step!(agent, model2, ::GridAgentSix)
128+
function agent_step!(agent, model2, ::GridAgentSix)
121129
agent.eight += sum(rand(abmrng(model2), (0, 1)) for a in nearby_agents(agent, model2))
122130
end
123131

0 commit comments

Comments
 (0)