Skip to content

Commit 0929bc5

Browse files
committed
Fix selection of particlefiles for writing
Looking at time_nextloop instead. We might rework the kernel loop in future (and the responsibilities of time, time_nextloop, as well as their effect on particle writing).
1 parent ffcb604 commit 0929bc5

File tree

3 files changed

+32
-4
lines changed

3 files changed

+32
-4
lines changed

parcels/particlefile.py

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -283,18 +283,22 @@ def _to_write_particles(particle_data, time):
283283
return np.where(
284284
(
285285
np.less_equal(
286-
time - np.abs(particle_data["dt"] / 2), particle_data["time"], where=np.isfinite(particle_data["time"])
286+
time - np.abs(particle_data["dt"] / 2),
287+
particle_data["time_nextloop"],
288+
where=np.isfinite(particle_data["time_nextloop"]),
287289
)
288290
& np.greater_equal(
289-
time + np.abs(particle_data["dt"] / 2), particle_data["time"], where=np.isfinite(particle_data["time"])
291+
time + np.abs(particle_data["dt"] / 2),
292+
particle_data["time_nextloop"],
293+
where=np.isfinite(particle_data["time_nextloop"]),
290294
) # check time - dt/2 <= particle_data["time"] <= time + dt/2
291295
| (
292296
(np.isnan(particle_data["dt"]))
293-
& np.equal(time, particle_data["time"], where=np.isfinite(particle_data["time"]))
297+
& np.equal(time, particle_data["time_nextloop"], where=np.isfinite(particle_data["time_nextloop"]))
294298
) # or dt is NaN and time matches particle_data["time"]
295299
)
296300
& (np.isfinite(particle_data["trajectory"]))
297-
& (np.isfinite(particle_data["time"]))
301+
& (np.isfinite(particle_data["time_nextloop"]))
298302
)[0]
299303

300304

@@ -303,6 +307,9 @@ def _convert_particle_data_time_to_float_seconds(particle_data, time_interval):
303307
particle_data = particle_data.copy()
304308

305309
particle_data["time"] = ((particle_data["time"] - time_interval.left) / np.timedelta64(1, "s")).astype(np.float64)
310+
particle_data["time_nextloop"] = (
311+
(particle_data["time_nextloop"] - time_interval.left) / np.timedelta64(1, "s")
312+
).astype(np.float64)
306313
particle_data["dt"] = (particle_data["dt"] / np.timedelta64(1, "s")).astype(np.float64)
307314
return particle_data
308315

tests/v4/test_advection.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,26 @@ def test_advection_zonal(mesh, npart=10):
5252
assert (np.diff(pset.lon) < 1.0e-4).all()
5353

5454

55+
def test_advection_zonal_with_particlefile(tmp_store):
56+
"""Particles at high latitude move geographically faster due to the pole correction in `GeographicPolar`."""
57+
npart = 10
58+
ds = simple_UV_dataset(mesh="flat")
59+
ds["U"].data[:] = 1.0
60+
grid = XGrid.from_dataset(ds, mesh="flat")
61+
U = Field("U", ds["U"], grid, interp_method=XLinear)
62+
V = Field("V", ds["V"], grid, interp_method=XLinear)
63+
UV = VectorField("UV", U, V)
64+
fieldset = FieldSet([U, V, UV])
65+
66+
pset = ParticleSet(fieldset, lon=np.zeros(npart) + 20.0, lat=np.linspace(0, 80, npart))
67+
pfile = pset.ParticleFile(tmp_store, outputdt=np.timedelta64(15, "m"))
68+
pset.execute(AdvectionRK4, runtime=np.timedelta64(2, "h"), dt=np.timedelta64(15, "m"), output_file=pfile)
69+
70+
assert (np.diff(pset.lon) < 1.0e-4).all()
71+
ds = xr.open_zarr(tmp_store)
72+
breakpoint()
73+
74+
5575
def periodicBC(particle, fieldset, time):
5676
particle.total_dlon += particle.dlon
5777
particle.lon = np.fmod(particle.lon, 2)

tests/v4/test_particlefile.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -385,6 +385,7 @@ def test_particlefile_write_particle_data(tmp_store):
385385
time_interval=time_interval,
386386
initial={
387387
"time": np.full(nparticles, fill_value=left),
388+
"time_nextloop": np.full(nparticles, fill_value=left),
388389
"lon": initial_lon,
389390
"dt": np.full(nparticles, fill_value=1.0),
390391
"trajectory": np.arange(nparticles),

0 commit comments

Comments
 (0)