1
0
Fork 0
mirror of https://gitlab.rlp.net/mobitar/ReCo.jl.git synced 2024-12-21 00:51:21 +00:00

Added radial distribution function

This commit is contained in:
Mo8it 2022-01-24 20:43:37 +01:00
parent 6cbc855e45
commit 3e02920067
10 changed files with 481 additions and 202 deletions

View file

@ -5,9 +5,11 @@ version = "0.2.0"
[deps] [deps]
BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf" BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf"
CSV = "336ed68f-0bac-5ca0-87d4-7b16caf5d00b"
CairoMakie = "13f3f980-e62b-5c42-98c6-ff1f3baf88f0" CairoMakie = "13f3f980-e62b-5c42-98c6-ff1f3baf88f0"
CellListMap = "69e1c6dd-3888-40e6-b3c8-31ac5f578864" CellListMap = "69e1c6dd-3888-40e6-b3c8-31ac5f578864"
ColorSchemes = "35d6a980-a343-548e-a6ea-1d62b119f2f4" ColorSchemes = "35d6a980-a343-548e-a6ea-1d62b119f2f4"
DataFrames = "a93c6f00-e57d-5684-b7b6-d8193f3e46c0"
Dates = "ade2ca70-3891-5945-98fb-dc099432e06a" Dates = "ade2ca70-3891-5945-98fb-dc099432e06a"
Distributions = "31c24e10-a181-5473-b8eb-7969acd0382f" Distributions = "31c24e10-a181-5473-b8eb-7969acd0382f"
Flux = "587475ba-b771-5e3f-ad9e-33799f191a9c" Flux = "587475ba-b771-5e3f-ad9e-33799f191a9c"

View file

@ -9,6 +9,8 @@ using ProgressMeter: ProgressMeter
using ReCo: ReCo using ReCo: ReCo
includet("../graphics/common_CairoMakie.jl")
# IMPORTANT: Disable the periodic boundary conditions # IMPORTANT: Disable the periodic boundary conditions
# The arguments types have to match for the function to be overwritten! # The arguments types have to match for the function to be overwritten!
ReCo.push_to_verlet_list!(::Any, ::Any, ::Any) = nothing ReCo.push_to_verlet_list!(::Any, ::Any, ::Any) = nothing
@ -26,20 +28,6 @@ ReCo.minimum_image(v::SVector{2,Float64}, ::Float64) = v
const δt = 1e-4 const δt = 1e-4
const Dₜ = ReCo.DEFAULT_Dₜ const Dₜ = ReCo.DEFAULT_Dₜ
function fill_with_bundle_property!(
v::Vector, property::Symbol, sim_dir::String, first_bundle::Int64=1
)
bundle_paths = ReCo.sorted_bundle_paths(sim_dir)
for i in first_bundle:length(bundle_paths)
bundle::ReCo.Bundle = JLD2.load_object(bundle_paths[i])
append!(v, getproperty(bundle, property))
end
return nothing
end
function max_possible_displacement(T::Float64, v₀::Float64, δt::Float64=δt, Dₜ::Float64=Dₜ) function max_possible_displacement(T::Float64, v₀::Float64, δt::Float64=δt, Dₜ::Float64=Dₜ)
return T * v₀ + T / δt * sqrt(2 * Dₜ * δt) return T * v₀ + T / δt * sqrt(2 * Dₜ * δt)
end end
@ -52,6 +40,8 @@ function msd_simulation(
parent_dir::String, parent_dir::String,
comment::String="", comment::String="",
) )
Random.seed!(42)
dir = ReCo.init_sim(; dir = ReCo.init_sim(;
n_particles=1, n_particles=1,
v₀=v₀, v₀=v₀,
@ -72,10 +62,8 @@ function msd_simulation(
end end
function mean_squared_displacement(; function mean_squared_displacement(;
n_simulations::Int64, v₀s::AbstractVector{Float64}, T::Float64 n_simulations::Int64, v₀s::NTuple{N,Float64}, T::Float64
) ) where {N}
Random.seed!(42)
n_v₀s = length(v₀s) n_v₀s = length(v₀s)
main_parent_dir = "mean_squared_displacement_$(Dates.now())" main_parent_dir = "mean_squared_displacement_$(Dates.now())"
@ -99,7 +87,9 @@ function mean_squared_displacement(;
end end
ts = Float64[] ts = Float64[]
fill_with_bundle_property!(ts, :t, sim_dirs[1, 1], 2) # Skip the first bundle to avoid t = 0 ReCo.append_bundle_properties!(
(ts,), (:t,), sim_dirs[1, 1]; particle_slice=1, snapshot_slice=:, first_bundle=2
) # Skip the first bundle to avoid t = 0
mean_sq_displacements = zeros((length(ts), n_v₀s)) mean_sq_displacements = zeros((length(ts), n_v₀s))
@ -137,42 +127,9 @@ function expected_mean_squared_displacement(t::Float64, v₀::Float64)
return (4 * Dₜ + 2 * v₀^2 / Dᵣ) * t + 2 * v₀^2 * (exp(-Dᵣ * t) - 1) / (Dᵣ^2) return (4 * Dₜ + 2 * v₀^2 / Dᵣ) * t + 2 * v₀^2 * (exp(-Dᵣ * t) - 1) / (Dᵣ^2)
end end
function init_cairomakie!()
CairoMakie.activate!()
set_theme!()
return nothing
end
function gen_figure()
text_width_in_pt = 405
return Figure(;
resolution=(text_width_in_pt, 0.55 * text_width_in_pt),
fontsize=10,
figure_padding=1,
)
end
function set_gaps!(fig::Figure)
colgap!(fig.layout, 5)
rowgap!(fig.layout, 5)
return nothing
end
function save_fig(filename::String, fig::Figure)
parent_dir = "exports/graphics"
mkpath(parent_dir)
return save("$parent_dir/$filename", fig; pt_per_unit=1)
end
function plot_mean_sq_displacement_with_expectation( function plot_mean_sq_displacement_with_expectation(
ts::Vector{Float64}, ts::Vector{Float64}, mean_sq_displacements::Matrix{Float64}, v₀s::NTuple{N,Float64}
mean_sq_displacements::Matrix{Float64}, ) where {N}
v₀s::AbstractVector{Float64},
)
init_cairomakie!() init_cairomakie!()
fig = gen_figure() fig = gen_figure()
@ -205,7 +162,7 @@ function plot_mean_sq_displacement_with_expectation(
end end
function run_msd_analysis() function run_msd_analysis()
v₀s = SVector(0.0, 20.0, 40.0, 60.0, 80.0) v₀s = (0.0, 20.0, 40.0, 60.0, 80.0)
ts, mean_sq_displacements = mean_squared_displacement(; ts, mean_sq_displacements = mean_squared_displacement(;
n_simulations=200 * Threads.nthreads(), v₀s=v₀s, T=100.0 n_simulations=200 * Threads.nthreads(), v₀s=v₀s, T=100.0
@ -216,17 +173,17 @@ function run_msd_analysis()
return nothing return nothing
end end
function plot_random_walk(T::Float64, v₀::Float64, seed::Int64) function plot_random_walk(; T::Float64, v₀::Float64, seed::Int64)
Random.seed!(seed) Random.seed!(seed)
half_box_len = max_possible_displacement(T, v₀) half_box_len = max_possible_displacement(T, v₀)
dir = msd_simulation(v₀, half_box_len, T, 8.0, "random_walk_$(Dates.now())") dir = msd_simulation(v₀, half_box_len, T, 8.0, "random_walk_$(Dates.now())")
ts = Float64[] ts = Float64[]
fill_with_bundle_property!(ts, :t, dir)
cs = SVector{2,Float64}[] cs = SVector{2,Float64}[]
fill_with_bundle_property!(cs, :c, dir) ReCo.append_bundle_properties!(
(ts, cs), (:t, :c), dir; particle_slice=1, snapshot_slice=:
)
init_cairomakie!() init_cairomakie!()
@ -281,7 +238,7 @@ function plot_random_walk(T::Float64, v₀::Float64, seed::Int64)
end end
function run_random_walk() function run_random_walk()
plot_random_walk(100_000.0, 0.0, 12345) plot_random_walk(; T=100_000.0, v₀=0.0, seed=12345)
return nothing return nothing
end end

View file

@ -1,28 +0,0 @@
if splitdir(pwd())[2] == "analysis"
cd("..")
end
if splitdir(pwd())[2] != "ReCo.jl"
error("You have to be in the main directeory ReCo.jl!")
else
include("src/analysis/pair_correlation_function.jl")
end
##
using JLD2: JLD2
using CairoMakie
CairoMakie.activate!()
set_theme!(theme_black())
##
dirs = readdir("exports/2021_11_19"; join=true)
##
for dir in dirs
data = JLD2.load("$dir/data.jld2")
display(pair_correlation(data["sol"], data["variables"]).fig)
end

View file

@ -0,0 +1,149 @@
# Source: https://www.researchgate.net/publication/223333736_Reconstruction_of_Ross'_linear-mixing_model_for_the_equation_of_state_of_deuterium
r_d_ratio,g_of_r_d_ratio
0.99392,0.08604
0.99388,0.18421
0.99384,0.28847
0.99382,0.34463
0.99378,0.42994
0.99372,0.52947
0.99365,0.63441
0.99361,0.68891
0.99354,0.77406
0.99344,0.87468
0.99332,0.98013
0.99325,1.03317
0.99314,1.11822
0.99297,1.21964
0.99278,1.32539
0.99267,1.37722
0.99249,1.4622
0.99224,1.56412
0.99194,1.67
0.99179,1.72089
0.99152,1.8058
0.99116,1.90793
0.99074,2.01372
0.99053,2.06399
0.99015,2.1488
0.98965,2.25086
0.98909,2.35636
0.98881,2.40637
0.98831,2.49108
0.98767,2.5925
0.98699,2.69664
0.98665,2.74669
0.98607,2.83091
0.98538,2.92885
0.98467,3.02834
0.98395,3.12761
0.98362,3.17414
0.98304,3.25677
0.98242,3.34772
0.98183,3.43776
0.98129,3.52581
0.98081,3.61118
0.98043,3.69358
0.98015,3.77322
0.98,3.85156
0.98014,3.95169
0.98089,4.03823
0.98357,4.10894
0.9944,4.032
1.00014,3.93792
1.00441,3.85868
1.00862,3.77571
1.01272,3.69218
1.01669,3.61072
1.0216,3.51176
1.02638,3.42062
1.03128,3.33517
1.03664,3.25085
1.04281,3.16285
1.04804,3.09295
1.05614,2.98982
1.06293,2.90588
1.07039,2.81547
1.07549,2.75441
1.08352,2.65945
1.09202,2.56047
1.09758,2.49642
1.10625,2.39796
1.11214,2.33189
1.12071,2.23742
1.12939,2.14379
1.13793,2.05435
1.14612,1.97171
1.15388,1.89756
1.16359,1.81176
1.17456,1.72585
1.18615,1.64833
1.19996,1.56268
1.21169,1.47967
1.22345,1.39143
1.23543,1.30583
1.24773,1.23043
1.26375,1.14911
1.28235,1.06205
1.30026,0.97628
1.32001,0.89731
1.34607,0.8185
1.38029,0.74139
1.42373,0.67706
1.47928,0.62965
1.54985,0.64005
1.60887,0.68208
1.65956,0.742
1.70693,0.80174
1.75549,0.86677
1.7997,0.93281
1.8408,0.99879
1.88278,1.07151
1.92418,1.14479
1.96069,1.20961
2.00089,1.27998
2.06624,1.29427
2.12188,1.24296
2.16454,1.1732
2.20365,1.10578
2.2468,1.03273
2.28968,0.97094
2.34711,0.92061
2.40659,0.87706
2.47617,0.86598
2.54506,0.87775
2.6091,0.91495
2.67198,0.9548
2.73415,0.99707
2.79524,1.03776
2.86004,1.06782
2.92949,1.08716
2.99726,1.09694
3.06572,1.07401
3.13305,1.0512
3.20406,1.01975
3.26722,0.99225
3.33163,0.96833
3.40415,0.95312
3.46976,0.95561
3.53944,0.96948
3.61034,0.98695
3.68191,1.00826
3.74431,1.02656
3.81351,1.04126
3.88832,1.04634
3.95948,1.04227
4.02721,1.03357
4.09307,1.02294
4.16757,1.01022
4.23256,0.99784
4.30367,0.98757
4.3786,0.98803
4.44527,0.99118
4.51289,0.99726
4.58223,1.00774
4.65288,1.01261
4.72314,1.01386
4.79174,1.02311
4.86131,1.03134
4.93191,1.0253
4.98585,1.01943
1 # Source: https://www.researchgate.net/publication/223333736_Reconstruction_of_Ross'_linear-mixing_model_for_the_equation_of_state_of_deuterium
2 r_d_ratio,g_of_r_d_ratio
3 0.99392,0.08604
4 0.99388,0.18421
5 0.99384,0.28847
6 0.99382,0.34463
7 0.99378,0.42994
8 0.99372,0.52947
9 0.99365,0.63441
10 0.99361,0.68891
11 0.99354,0.77406
12 0.99344,0.87468
13 0.99332,0.98013
14 0.99325,1.03317
15 0.99314,1.11822
16 0.99297,1.21964
17 0.99278,1.32539
18 0.99267,1.37722
19 0.99249,1.4622
20 0.99224,1.56412
21 0.99194,1.67
22 0.99179,1.72089
23 0.99152,1.8058
24 0.99116,1.90793
25 0.99074,2.01372
26 0.99053,2.06399
27 0.99015,2.1488
28 0.98965,2.25086
29 0.98909,2.35636
30 0.98881,2.40637
31 0.98831,2.49108
32 0.98767,2.5925
33 0.98699,2.69664
34 0.98665,2.74669
35 0.98607,2.83091
36 0.98538,2.92885
37 0.98467,3.02834
38 0.98395,3.12761
39 0.98362,3.17414
40 0.98304,3.25677
41 0.98242,3.34772
42 0.98183,3.43776
43 0.98129,3.52581
44 0.98081,3.61118
45 0.98043,3.69358
46 0.98015,3.77322
47 0.98,3.85156
48 0.98014,3.95169
49 0.98089,4.03823
50 0.98357,4.10894
51 0.9944,4.032
52 1.00014,3.93792
53 1.00441,3.85868
54 1.00862,3.77571
55 1.01272,3.69218
56 1.01669,3.61072
57 1.0216,3.51176
58 1.02638,3.42062
59 1.03128,3.33517
60 1.03664,3.25085
61 1.04281,3.16285
62 1.04804,3.09295
63 1.05614,2.98982
64 1.06293,2.90588
65 1.07039,2.81547
66 1.07549,2.75441
67 1.08352,2.65945
68 1.09202,2.56047
69 1.09758,2.49642
70 1.10625,2.39796
71 1.11214,2.33189
72 1.12071,2.23742
73 1.12939,2.14379
74 1.13793,2.05435
75 1.14612,1.97171
76 1.15388,1.89756
77 1.16359,1.81176
78 1.17456,1.72585
79 1.18615,1.64833
80 1.19996,1.56268
81 1.21169,1.47967
82 1.22345,1.39143
83 1.23543,1.30583
84 1.24773,1.23043
85 1.26375,1.14911
86 1.28235,1.06205
87 1.30026,0.97628
88 1.32001,0.89731
89 1.34607,0.8185
90 1.38029,0.74139
91 1.42373,0.67706
92 1.47928,0.62965
93 1.54985,0.64005
94 1.60887,0.68208
95 1.65956,0.742
96 1.70693,0.80174
97 1.75549,0.86677
98 1.7997,0.93281
99 1.8408,0.99879
100 1.88278,1.07151
101 1.92418,1.14479
102 1.96069,1.20961
103 2.00089,1.27998
104 2.06624,1.29427
105 2.12188,1.24296
106 2.16454,1.1732
107 2.20365,1.10578
108 2.2468,1.03273
109 2.28968,0.97094
110 2.34711,0.92061
111 2.40659,0.87706
112 2.47617,0.86598
113 2.54506,0.87775
114 2.6091,0.91495
115 2.67198,0.9548
116 2.73415,0.99707
117 2.79524,1.03776
118 2.86004,1.06782
119 2.92949,1.08716
120 2.99726,1.09694
121 3.06572,1.07401
122 3.13305,1.0512
123 3.20406,1.01975
124 3.26722,0.99225
125 3.33163,0.96833
126 3.40415,0.95312
127 3.46976,0.95561
128 3.53944,0.96948
129 3.61034,0.98695
130 3.68191,1.00826
131 3.74431,1.02656
132 3.81351,1.04126
133 3.88832,1.04634
134 3.95948,1.04227
135 4.02721,1.03357
136 4.09307,1.02294
137 4.16757,1.01022
138 4.23256,0.99784
139 4.30367,0.98757
140 4.3786,0.98803
141 4.44527,0.99118
142 4.51289,0.99726
143 4.58223,1.00774
144 4.65288,1.01261
145 4.72314,1.01386
146 4.79174,1.02311
147 4.86131,1.03134
148 4.93191,1.0253
149 4.98585,1.01943

View file

@ -0,0 +1,216 @@
using CairoMakie
using LaTeXStrings: @L_str
using StaticArrays: SVector
using JLD2: JLD2
using Dates: Dates
using CSV: CSV
using DataFrames: DataFrames
using Random: Random
using ReCo: ReCo
includet("../../graphics/common_CairoMakie.jl")
function radial_distribution_simulation(;
n_particles::Int64, v₀s::NTuple{N,Float64}, T::Float64, packing_ratio::Float64
) where {N}
Random.seed!(42)
n_v₀s = length(v₀s)
sim_dirs = Vector{String}(undef, n_v₀s)
parent_dir = "radial_distribution_$(Dates.now())"
Threads.@threads for v₀_ind in 1:n_v₀s
v₀ = v₀s[v₀_ind]
dir = ReCo.init_sim(;
n_particles=n_particles,
v₀=v₀,
packing_ratio=packing_ratio,
parent_dir=parent_dir,
comment="$v₀",
)
ReCo.run_sim(dir; duration=T, seed=v₀_ind)
sim_dirs[v₀_ind] = dir
end
return sim_dirs
end
function circular_shell_volume(lower_radius, Δradius)
return π * (2 * lower_radius * Δradius + Δradius^2)
end
function radial_distribution(;
sim_dirs::Vector{String}, n_radii::Int64, n_last_snapshots::Int64, n_particles::Int64
)
sim_consts::ReCo.SimConsts = JLD2.load_object("$(sim_dirs[1])/sim_consts.jld2")
particle_radius = sim_consts.particle_radius
min_lower_radius = 0.0
max_lower_radius = 5 * (2 * particle_radius)
Δradius = (max_lower_radius - min_lower_radius) / n_radii
lower_radii = LinRange(min_lower_radius, max_lower_radius, n_radii)
box_volume = (2 * sim_consts.half_box_len)^2
volume_per_particle = box_volume / n_particles
n_sim_dirs = length(sim_dirs)
gs = Vector{Vector{Float64}}(undef, n_sim_dirs)
Threads.@threads for sim_dir_ind in 1:n_sim_dirs
sim_dir = sim_dirs[sim_dir_ind]
cs = Matrix{SVector{2,Float64}}(undef, (n_particles, n_last_snapshots))
bundle_paths = ReCo.sorted_bundle_paths(sim_dir; rev=true)
snapshot_conunter = 0
break_bundle_path_loop = false
for bundle_path in bundle_paths
bundle::ReCo.Bundle = JLD2.load_object(bundle_path)
for snapshot_ind in (bundle.n_snapshots):-1:1
snapshot_conunter += 1
@simd for particle_ind in 1:n_particles
cs[particle_ind, snapshot_conunter] = bundle.c[
particle_ind, snapshot_ind
]
end
if snapshot_conunter == n_last_snapshots
break_bundle_path_loop = true
break
end
end
if break_bundle_path_loop
break
end
end
if snapshot_conunter != n_last_snapshots
error("snapshot_conunter != n_last_snapshots")
end
g = zeros(n_radii)
for snapshot_ind in 1:n_last_snapshots
for p1_ind in 1:n_particles
for p2_ind in (p1_ind + 1):n_particles
c1 = cs[p1_ind, snapshot_ind]
c2 = cs[p2_ind, snapshot_ind]
r⃗₁₂ = c2 - c1
r⃗₁₂ = ReCo.minimum_image(r⃗₁₂, sim_consts.half_box_len)
distance = ReCo.norm2d(r⃗₁₂)
lower_radius_ind = ceil(Int64, distance / Δradius)
if lower_radius_ind <= n_radii
g[lower_radius_ind] += 2
end
end
end
end
for (lower_radius_ind, lower_radius) in enumerate(lower_radii)
g[lower_radius_ind] *=
volume_per_particle / (
n_last_snapshots *
n_particles *
circular_shell_volume(lower_radius, Δradius)
)
end
gs[sim_dir_ind] = g
end
return (lower_radii, gs, particle_radius)
end
function plot_radial_distributions(
v₀s::NTuple{N,Float64},
lower_radii::AbstractVector{Float64},
gs::Vector{Vector{Float64}},
particle_radius::Float64,
) where {N}
println("Plotting the radial distributions")
init_cairomakie!()
fig = gen_figure()
max_lower_radius = maximum(lower_radii)
max_g = maximum(maximum.(gs))
ax = Axis(
fig[1:2, 1:2];
xticks=0:(2 * particle_radius):ceil(Int64, max_lower_radius),
yticks=0:ceil(Int64, max_g),
xlabel=L"r / d",
ylabel=L"g",
)
lines!(
ax,
SVector(0.0, max_lower_radius),
SVector(1.0, 1.0);
linestyle=:dash,
color=:red,
linewidth=1,
)
expected = CSV.read(
"analysis/g_of_r_d_ratio_with_0_45_packing_ratio.csv",
DataFrames.DataFrame;
header=2,
)
lines!(
ax,
expected.r_d_ratio,
expected.g_of_r_d_ratio;
label="Expectation for dense hard spheres",
color=:green,
)
for (g_ind, g) in enumerate(gs)
scatterlines!(
ax, lower_radii, g; markersize=3, linewidth=0.5, label=L"v_0 = %$(v₀s[g_ind])"
)
end
axislegend(ax; position=:rt, padding=3, rowgap=-3)
save_fig("radial_distribution.pdf", fig)
return nothing
end
function run_radial_distribution_analysis()
v₀s = (0.0, 80.0)
n_particles = 1000
sim_dirs = radial_distribution_simulation(;
n_particles=n_particles, v₀s=v₀s, T=100.0, packing_ratio=0.45
)
lower_radii, gs, particle_radius = radial_distribution(;
sim_dirs=sim_dirs, n_radii=75, n_last_snapshots=200, n_particles=n_particles
)
plot_radial_distributions(v₀s, lower_radii, gs, particle_radius)
return nothing
end

View file

@ -0,0 +1,29 @@
function init_cairomakie!()
CairoMakie.activate!()
set_theme!()
return nothing
end
function gen_figure(; padding=4)
text_width_in_pt = 405
return Figure(;
resolution=(text_width_in_pt, 0.55 * text_width_in_pt),
fontsize=10,
figure_padding=padding,
)
end
function set_gaps!(fig::Figure)
colgap!(fig.layout, 5)
rowgap!(fig.layout, 5)
return nothing
end
function save_fig(filename::String, fig::Figure, parent_dir="exports/graphics")
mkpath(parent_dir)
return save("$parent_dir/$filename", fig; pt_per_unit=1)
end

View file

@ -1,6 +1,8 @@
using CairoMakie using CairoMakie
using LaTeXStrings: @L_str using LaTeXStrings: @L_str
includet("common_CairoMakie.jl")
const minimum_r_σ_ratio = 2^(1 / 6) const minimum_r_σ_ratio = 2^(1 / 6)
function U_LJ_ϵ_ratio(r_σ_ratio::Real) function U_LJ_ϵ_ratio(r_σ_ratio::Real)
@ -16,11 +18,10 @@ function U_WCA_ϵ_ratio(r_σ_ratio::Real)
end end
end end
text_width_in_pt = 405 function plot_potentials()
init_cairomakie!()
fig = Figure(; fig = gen_figure()
resolution=(text_width_in_pt, 0.55 * text_width_in_pt), fontsize=10, figure_padding=1
)
max_x = 2.5 max_x = 2.5
@ -36,7 +37,11 @@ LJ = lines!(ax, r_σ_ratio, U_LJ_ϵ_ratio.(r_σ_ratio))
WCA = lines!(ax, r_σ_ratio, U_WCA_ϵ_ratio.(r_σ_ratio)) WCA = lines!(ax, r_σ_ratio, U_WCA_ϵ_ratio.(r_σ_ratio))
minimum_r_σ_ratio_line = lines!( minimum_r_σ_ratio_line = lines!(
ax, [minimum_r_σ_ratio, minimum_r_σ_ratio], [min_y, max_y]; linestyle=:dash, linewidth=1 ax,
[minimum_r_σ_ratio, minimum_r_σ_ratio],
[min_y, max_y];
linestyle=:dash,
linewidth=1,
) )
Legend( Legend(
@ -45,7 +50,9 @@ Legend(
[L"U_{LJ}", L"U_{WCA}", L"\frac{r}{σ} = 2^{1/6}"], [L"U_{LJ}", L"U_{WCA}", L"\frac{r}{σ} = 2^{1/6}"],
) )
colgap!(fig.layout, 5) set_gaps!(fig)
rowgap!(fig.layout, 5)
save("exports/graphics/potential.pdf", fig; pt_per_unit=1) save_fig("potential.pdf", fig)
return nothing
end

View file

@ -124,12 +124,7 @@ function run_rl(;
agent(PRE_EPISODE_STAGE, env) agent(PRE_EPISODE_STAGE, env)
# Episode # Episode
ReCo.run_sim( ReCo.run_sim(dir; duration=episode_duration, seed=episode, env_helper=env_helper)
dir;
duration=episode_duration,
seed=rand(1:typemax(Int64)),
env_helper=env_helper,
)
env.shared.terminated = true env.shared.terminated = true

View file

@ -1,83 +0,0 @@
using CairoMakie, LaTeXStrings
using LoopVectorization: @turbo
using ReCo: minimum_image, norm2d
function plot_g(radius, g, variables)
fig = Figure()
ax = Axis(
fig[1, 1];
xticks=0:ceil(Int64, maximum(radius)),
yticks=0:ceil(Int64, maximum(g)),
xlabel=L"r",
ylabel=L"g(r)",
title="v₀ = $(variables.v₀)",
)
scatterlines!(ax, radius, g; color=:white, markercolor=:red)
return fig
end
function pair_correlation(sol, variables)
n_r = 100
n_last_frames = 200
min_radius = variables.particle_diameter / 2
max_radius = 10.0 * variables.particle_diameter
dr = (max_radius - min_radius) / n_r
radius = range(min_radius, max_radius; length=n_r)
N_g = zeros(variables.n_particles, n_r)
Threads.@threads for r_ind in 1:n_r
r = radius[r_ind]
@simd for i in 1:(variables.n_particles)
for j in 1:(variables.n_particles)
if i != j
for k in 1:n_last_frames
frame = variables.n_snapshots - k + 1
c1 = sol.center[i, frame]
c2 = sol.center[j, frame]
r⃗₁₂ = c1 - c2
r⃗₁₂ = minimum_image(r⃗₁₂, variables.half_box_len)
distance = norm2d(r⃗₁₂)
if (distance >= r) && (distance <= r + dr)
N_g[i, r_ind] += 1
end
end
end
end
end
end
g = zeros(n_r)
@simd for r_ind in 1:n_r
r = radius[r_ind]
tmp_g = 0.0
@turbo for i in 1:(variables.n_particles)
tmp_g += N_g[i, r_ind]
end
tmp_g *=
(2 * variables.half_box_len)^2 / (
(variables.n_particles * n_last_frames) *
variables.n_particles *
2 *
π *
r *
dr
)
g[r_ind] = tmp_g
end
fig = plot_g(radius, g, variables)
return (; fig, radius, g)
end

View file

@ -39,6 +39,9 @@ struct Bundle
t::Vector{Float64} t::Vector{Float64}
c::Matrix{SVector{2,Float64}} c::Matrix{SVector{2,Float64}}
φ::Matrix{Float64} φ::Matrix{Float64}
n_particles::Int64
n_snapshots::Int64
end end
function Bundle(n_particles::Int64, n_snapshots::Int64) function Bundle(n_particles::Int64, n_snapshots::Int64)
@ -46,11 +49,13 @@ function Bundle(n_particles::Int64, n_snapshots::Int64)
Vector{Float64}(undef, n_snapshots), Vector{Float64}(undef, n_snapshots),
Matrix{SVector{2,Float64}}(undef, (n_particles, n_snapshots)), Matrix{SVector{2,Float64}}(undef, (n_particles, n_snapshots)),
Matrix{Float64}(undef, (n_particles, n_snapshots)), Matrix{Float64}(undef, (n_particles, n_snapshots)),
n_particles,
n_snapshots,
) )
end end
function first_n_snapshots(bundle::Bundle, n::Int64) function first_n_snapshots(bundle::Bundle, n::Int64)
return Bundle(bundle.t[1:n], bundle.c[:, 1:n], bundle.φ[:, 1:n]) return Bundle(bundle.t[1:n], bundle.c[:, 1:n], bundle.φ[:, 1:n], bundle.n_particles, n)
end end
function save_snapshot!( function save_snapshot!(
@ -78,7 +83,7 @@ function save_bundle(dir::String, bundle::Bundle, n_bundle::Int64, T::Float64)
return nothing return nothing
end end
function sorted_bundle_paths(dir::String) function sorted_bundle_paths(dir::String; rev::Bool=false)
bundle_paths = readdir("$dir/bundles"; join=true, sort=false) bundle_paths = readdir("$dir/bundles"; join=true, sort=false)
n_bundles = length(bundle_paths) n_bundles = length(bundle_paths)
@ -93,7 +98,37 @@ function sorted_bundle_paths(dir::String)
bundle_nums[i] = parse(Int64, bundle_num_string) bundle_nums[i] = parse(Int64, bundle_num_string)
end end
sort_perm = sortperm(bundle_nums) sort_perm = sortperm(bundle_nums; rev=rev)
return bundle_paths[sort_perm] return bundle_paths[sort_perm]
end end
function append_bundle_properties!(
vs::NTuple{N,Vector},
properties::NTuple{N,Symbol},
sim_dir::String;
particle_slice=nothing,
snapshot_slice,
first_bundle::Int64=1,
) where {N}
bundle_paths = ReCo.sorted_bundle_paths(sim_dir)
for i in first_bundle:length(bundle_paths)
bundle::ReCo.Bundle = JLD2.load_object(bundle_paths[i])
for (v_ind, v) in enumerat(vs)
property = properties[v_ind]
bundle_property = getproperty(bundle, property)
if !isnothing(particle_slice)
bundle_property_view = view(bundle_property, particle_slice, snapshot_slice)
else
bundle_property_view = view(bundle_property, snapshot_slice)
end
append!(v, bundle_property_view)
end
end
return nothing
end