Skip to content

Commit c812245

Browse files
authored
Default seed for a System is generated from the task-local RNG (#334)
1 parent e6216f7 commit c812245

File tree

12 files changed

+57
-52
lines changed

12 files changed

+57
-52
lines changed

docs/make.jl

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ function build_examples(example_sources, destdir)
3737
"""
3838
# Download this example as [Julia file]($assetsdir/scripts/$name.jl) or [Jupyter notebook]($assetsdir/notebooks/$name.ipynb).
3939
40+
import Random; Random.seed!(0); #hide
4041
""" * str
4142
end
4243
# Write to `src/$destpath/$name.md`

docs/src/parallelism.md

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -15,19 +15,20 @@ copied and pasted into your preferred Julia development environment.
1515

1616
The serial approach to calculating a structure factor, covered in the [FeI₂
1717
tutorial](@ref "4. Generalized spin dynamics of FeI₂ at finite *T*"), involves
18-
thermalizing a spin `System` and then calling [`add_sample!`](@ref).
18+
thermalizing a spin [`System`](@ref) and then calling [`add_sample!`](@ref).
1919
`add_sample!` uses the state of the `System` as an initial condition for the
2020
calculation of a dynamical trajectory. The correlations of the trajectory are
2121
calculated and accumulated into a running average of the ``\mathcal{S}(𝐪,ω)``.
2222
This sequence is repeated to generate additional samples.
2323

2424
To illustrate, we'll set up a a simple model: a spin-1 antiferromagnet on a BCC
25-
crystal.
25+
crystal. Constructing the `System` with a specific random number `seed` ensures
26+
full reproducibility of the simulation.
2627

2728
```julia
2829
using Sunny, GLMakie
2930

30-
function make_system(; seed=nothing)
31+
function make_system(seed)
3132
latvecs = lattice_vectors(1, 1, 1, 90, 90, 90)
3233
positions = [[0, 0, 0]/2, [1, 1, 1]/2]
3334
cryst = Crystal(latvecs, positions)
@@ -36,7 +37,7 @@ function make_system(; seed=nothing)
3637
return sys
3738
end
3839

39-
sys = make_system()
40+
sys = make_system(0)
4041
```
4142

4243
A serial calculation of [`SampledCorrelations`](@ref) involving the
@@ -80,11 +81,12 @@ Before going further, make sure that `Threads.nthreads()` returns a number great
8081

8182
We will use multithreading in a very simple way, essentially employing a
8283
distributed memory approach to avoid conflicts around memory access. First
83-
preallocate a number of systems and correlations.
84+
preallocate a number of systems and correlations. The integer `id` of each
85+
system is used as its random number seed.
8486

8587
```julia
8688
npar = Threads.nthreads()
87-
systems = [make_system(; seed=id) for id in 1:npar]
89+
systems = [make_system(id) for id in 1:npar]
8890
scs = [SampledCorrelations(sys; dt=0.1, energies, measure) for _ in 1:npar]
8991
```
9092

@@ -151,7 +153,7 @@ environments. This is easily achieved with the `@everywhere` macro.
151153
```julia
152154
@everywhere using Sunny
153155

154-
@everywhere function make_system(; seed=nothing)
156+
@everywhere function make_system(seed)
155157
latvecs = lattice_vectors(1, 1, 1, 90, 90, 90)
156158
positions = [[0, 0, 0]/2, [1, 1, 1]/2]
157159
cryst = Crystal(latvecs, positions)
@@ -181,7 +183,7 @@ called `scs`.
181183

182184
```julia
183185
scs = pmap(1:ncores) do id
184-
sys = make_system(; seed=id)
186+
sys = make_system(id)
185187
sc = SampledCorrelations(sys; dt=0.1, energies, measure)
186188
integrator = Langevin(0.05; damping=0.2, kT=0.5)
187189

docs/src/versions.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@
66
* Better error message when a $g$-tensor is symmetry disallowed.
77
* Higher-precision convergence in [`minimize_energy!`](@ref).
88
* Fix [`minimize_energy!`](@ref) when used with [`set_vacancy_at!`](@ref).
9+
* The `System` constructor now, by default, seeds its internal random number
10+
generator with `seed=rand(UInt)`. Note that Julia's global random number
11+
generator can itself be seeded with `Random.seed!`.
912

1013
## v0.7.3
1114
(Nov 12, 2024)

examples/02_LLD_CoRh2O4.jl

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,8 @@
99
# classical-to-quantum correction factor, the resulting intensities can be
1010
# compared to inelastic neutron scattering data.
1111

12-
# Construct the system as in the [previous tutorial](@ref "1. Spin wave
13-
# simulations of CoRh₂O₄"). For this antiferromagnetic model on the diamond
14-
# cubic lattice, the ground state is unfrustrated Néel order.
12+
# Construct the CoRh₂O₄ antiferromagnet as before. Energy minimization yields
13+
# the expected Néel order.
1514

1615
using Sunny, GLMakie
1716

@@ -22,7 +21,7 @@ cryst = Crystal(latvecs, [[1/8, 1/8, 1/8]], 227)
2221

2322
sys = System(cryst, [1 => Moment(s=3/2, g=2)], :dipole)
2423
J = 0.63 # (meV)
25-
set_exchange!(sys, J, Bond(2, 3, [0,0,0]))
24+
set_exchange!(sys, J, Bond(2, 3, [0, 0, 0]))
2625
randomize_spins!(sys)
2726
minimize_energy!(sys)
2827
plot_spins(sys; color=[S[3] for S in sys.dipoles])

examples/03_LSWT_SU3_FeI2.jl

Lines changed: 20 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -84,11 +84,11 @@ print_symmetry_table(cryst, 8.0)
8484
# magnitude. This physics is, however, well captured with a theory of SU(_N_)
8585
# coherent states, where ``N = 2S+1 = 3`` is the number of levels. Activate this
8686
# generalized theory by selecting `:SUN` mode instead of `:dipole` mode.
87-
#
88-
# An optional random number `seed` will make the calculations exactly
89-
# reproducible.
87+
#
88+
# An optional `seed` for random number generation can be used to to make the
89+
# calculation exactly reproducible.
9090

91-
sys = System(cryst, [1 => Moment(s=1, g=2)], :SUN, seed=2)
91+
sys = System(cryst, [1 => Moment(s=1, g=2)], :SUN; seed=2)
9292

9393
# Set the exchange interactions for FeI₂ following the fits of [Bai et
9494
# al.](https://doi.org/10.1038/s41567-020-01110-1)
@@ -156,42 +156,37 @@ sys = resize_supercell(sys, (4, 4, 4))
156156
randomize_spins!(sys)
157157
minimize_energy!(sys)
158158

159-
# A positive number above indicates that the procedure has converged to a local
160-
# energy minimum. The configuration, however, may still have defects. This can
161-
# be checked by visualizing the expected spin dipoles, colored according to
162-
# their ``z``-components.
159+
# The positive step-count above indicates successful convergence to a local
160+
# energy minimum. Defects, however, are visually apparent.
163161

164162
plot_spins(sys; color=[S[3] for S in sys.dipoles])
165163

166-
# To better understand the spin configuration, we could inspect the static
167-
# structure factor ``\mathcal{S}(𝐪)`` in the 3D space of momenta ``𝐪``. The
168-
# general tool for this analysis is [`SampledCorrelationsStatic`](@ref). For the
169-
# present purposes, however, it is more convenient to use
170-
# [`print_wrapped_intensities`](@ref), which reports ``\mathcal{S}(𝐪)`` with
171-
# periodic wrapping of all commensurate ``𝐪`` wavevectors into the first
172-
# Brillouin zone.
164+
# One could precisely quantify the Fourier-space static structure factor
165+
# ``\mathcal{S}(𝐪)`` of this spin configuration using
166+
# [`SampledCorrelationsStatic`](@ref). For the present purposes, however, it is
167+
# most convenient to use [`print_wrapped_intensities`](@ref), which effectively
168+
# averages ``\mathcal{S}(𝐪)`` over all Brillouin zones.
173169

174170
print_wrapped_intensities(sys)
175171

176172
# The known zero-field energy-minimizing magnetic structure of FeI₂ is a two-up,
177173
# two-down order. It can be described as a generalized spiral with a single
178174
# propagation wavevector ``𝐤``. Rotational symmetry allows for three equivalent
179175
# orientations: ``±𝐤 = [0, -1/4, 1/4]``, ``[1/4, 0, 1/4]``, or
180-
# ``[-1/4,1/4,1/4]``. Small systems can spontaneously break this symmetry, but
181-
# for larger systems, defects and competing domains are to be expected.
182-
# Nonetheless, `print_wrapped_intensities` shows large intensities consistent
183-
# with a subset of the known ordering wavevectors.
176+
# ``[-1/4,1/4,1/4]``. Energy minimization of large systems can easily get
177+
# trapped in a metastable state with competing domains and defects. Nonetheless,
178+
# `print_wrapped_intensities` shows that a non-trivial fraction of the total
179+
# intensity is consistent with known ordering wavevectors.
184180
#
185181
# Let's break the three-fold symmetry by hand. The function
186-
# [`suggest_magnetic_supercell`](@ref) takes one or more ``𝐤`` modes, and
187-
# suggests a magnetic cell shape that is commensurate.
182+
# [`suggest_magnetic_supercell`](@ref) takes any number of ``𝐤`` modes and
183+
# suggests a magnetic cell shape that is commensurate with all of them.
188184

189185
suggest_magnetic_supercell([[0, -1/4, 1/4]])
190186

191-
# Calling [`reshape_supercell`](@ref) yields a much smaller system, making it
192-
# much easier to find the global energy minimum. Plot the system again, now
193-
# including "ghost" spins out to 12Å, to verify that the magnetic order is
194-
# consistent with FeI₂.
187+
# Using the minimal system returned by [`reshape_supercell`](@ref), it is now
188+
# easy to find the ground state. Plot the system again, now including "ghost"
189+
# spins out to 12Å, to verify that the magnetic order is consistent with FeI₂.
195190

196191
sys_min = reshape_supercell(sys, [1 0 0; 0 2 1; 0 -2 1])
197192
randomize_spins!(sys_min)

examples/05_MC_Ising.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ crystal = Crystal(latvecs, [[0, 0, 0]])
1616
# dipole ``𝐒`` is ``-𝐁⋅𝐒``. The system size is 128×128.
1717

1818
L = 128
19-
sys = System(crystal, [1 => Moment(s=1, g=-1)], :dipole; dims=(L, L, 1), seed=0)
19+
sys = System(crystal, [1 => Moment(s=1, g=-1)], :dipole; dims=(L, L, 1))
2020
polarize_spins!(sys, (0, 0, 1))
2121

2222
# Use [`set_exchange!`](@ref) to include a ferromagnetic Heisenberg interaction

examples/07_Dipole_Dipole.jl

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,10 @@ positions = [[0, 0, 0]]
1818
cryst = Crystal(latvecs, positions, 227)
1919
view_crystal(cryst)
2020

21-
# Create a system and reshape to the primitive cell, which contains four atoms.
22-
# Add antiferromagnetic nearest neighbor exchange interactions.
21+
# Create a [`System`](@ref) with a random number `seed` that was empirically
22+
# selected to produce the desired type of spontaneous symmetry breaking. Reshape
23+
# to the primitive cell, which contains four atoms. Add antiferromagnetic
24+
# nearest neighbor exchange interactions.
2325

2426
sys = System(cryst, [1 => Moment(s=7/2, g=2)], :dipole; seed=0)
2527
sys = reshape_supercell(sys, primitive_cell(cryst))

examples/spinw_tutorials/SW10_Energy_cut.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ grid = q_space_grid(cryst, [1, 0, 0], range(0, 2, 201), [0, 1, 0], range(0, 2, 2
3333
# Apply a line broadening with a full-width half-max of 0.2 meV to approximately
3434
# capture intensities between 3.5 and 4.0 meV.
3535

36-
swt = SpinWaveTheory(sys; measure=ssf_perp(sys))
36+
swt = SpinWaveTheory(sys; measure=ssf_trace(sys))
3737
res = intensities(swt, grid; energies=[3.75], kernel=gaussian(fwhm=0.2))
3838
plot_intensities(res; units)
3939

examples/spinw_tutorials/SW15_Ba3NbFe3Si2O14.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ view_crystal(cryst)
3030
# [Loire et al., Phys. Rev. Lett. **106**, 207201
3131
# (2011)](http://dx.doi.org/10.1103/PhysRevLett.106.207201).
3232

33-
sys = System(cryst, [1 => Moment(s=5/2, g=2)], :dipole; seed=0)
33+
sys = System(cryst, [1 => Moment(s=5/2, g=2)], :dipole)
3434
J₁ = 0.85
3535
J₂ = 0.24
3636
J₃ = 0.053

examples/spinw_tutorials/SW18_Distorted_kagome.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ view_crystal(cryst)
2525
# Define the interactions.
2626

2727
moments = [1 => Moment(s=1/2, g=2), 3 => Moment(s=1/2, g=2)]
28-
sys = System(cryst, moments, :dipole, seed=0)
28+
sys = System(cryst, moments, :dipole)
2929
J = -2
3030
Jp = -1
3131
Jab = 0.75

0 commit comments

Comments
 (0)