Skip to content

PIC and FLIP ​

FLIP transfers combine particle values with grid updates. They are useful when pure PIC is too diffusive but pure FLIP is too noisy. JustPIC provides them in both directions and for both vertex and centroid grids:

DirectionVerticesCentroids
grid → particles (blend)grid2particle_flip!centroid2particle_flip!
particles → grid (increment)particle2grid_flip!particle2centroid_flip!

All of them accept single fields or tuples of fields in 2D and 3D, and run unchanged on every backend, including Float32.

Grid to particles ​

Given current grid field F, previous grid field F₀, and the existing particle field Fp:

julia
grid2particle_flip!(Fp, F, F₀, particles; α=0.5)

The blend parameter is:

αMethod
1pure PIC: replace with interpolated current-grid value
0pure FLIP: add the interpolated grid change to the particle value
between 0 and 1PIC/FLIP blend

Conceptually, the blend combines the current-grid estimate with the particle value plus the grid increment:

text
current grid ──interpolate──▶ PIC value ──┐
                                          ├── α PIC + (1 − α) FLIP ──▶ particle
old/current grids ──difference──▶ Δgrid ──┘
particle + Δgrid ───────────────────────▶ FLIP value

The usual time-step pattern is:

julia
F₀ .= F
# update F on the grid
grid2particle_flip!(Fp, F, F₀, particles; α=0.5)

The source arrays use the same ghost layout rules as grid2particle!; pass ghost_1, ghost_2, and ghost_3 when a direction is physical-only.

centroid2particle_flip!(Fp, F, F₀, particles; α) does the same with cell-centered fields in the particles.xci layout; its ghosted, ghost_1, ghost_2 and ghost_3 keywords are those of centroid2particle!.

Particles to grid ​

The reverse transfer accumulates the change of a particle field, Fp - Fp₀, onto a grid field with the same weights as particle2grid! and particle2centroid!:

julia
particle2grid_flip!(F, Fp, Fp₀, particles)      # F += Σ ω (Fp - Fp₀) / Σ ω
particle2centroid_flip!(Fc, Fp, Fp₀, particles)

F is only modified where at least one particle contributes (Σ ω ≠ 0), so the result carries over the previous grid value elsewhere. No temporary arrays or atomics are involved: each grid node gathers from the particles around it.

A complete example that uses both directions on a centroid field is in PIC/FLIP temperature update in 2D.

API ​

JustPIC.grid2particle_flip! Function
julia
grid2particle_flip!(Fp, F, F0, particles; α = 0.0)

Update particle values with a PIC/FLIP blend.

α = 1 gives pure PIC, α = 0 gives pure FLIP, and intermediate values blend between the two updates.

Arguments

  • Fp: particle field (or tuple of particle fields) to update in place.

  • F: current grid field (or tuple of fields).

  • F0: previous grid field (or tuple of fields), same layout as F.

  • particles: particle container; its vertex grid particles.xvi is used.

  • α: PIC fraction in the PIC/FLIP blend, in [0, 1].

  • ghost_1, ghost_2, ghost_3: whether F and F0 include ghost nodes in each coordinate direction. Disable a keyword for a physical-only direction.

Note

The older method grid2particle_flip!(Fp, xvi, F, F0, particles; ...) that takes the vertex coordinates explicitly is deprecated; use the method above.

source
JustPIC.centroid2particle_flip! Function
julia
centroid2particle_flip!(Fp, F, F0, particles; α = 0.0, ghosted = true)

Update particle values from cell-centered fields with a PIC/FLIP blend.

α = 1 gives pure PIC, α = 0 gives pure FLIP: Fp += F - F0, with F and F0 interpolated to the particle. Fp, F and F0 may be single fields or tuples of fields. See centroid2particle! for the ghosted, ghost_1, ghost_2 and ghost_3 keywords.

source
JustPIC.particle2grid_flip! Function
julia
particle2grid_flip!(F, Fp, Fp0, particles; ghost_1 = true, ghost_2 = true, ghost_3 = true)

Add the interpolated particle increment Fp - Fp0 to the grid nodes F: F += Σ ω (Fp - Fp0) / Σ ω, with the weights of particle2grid!.

F, Fp and Fp0 may be single fields or tuples of fields. Nodes with no surrounding particles are left unchanged.

Arguments

  • F: nodal array (or tuple of arrays) to update in place.

  • Fp: current particle field.

  • Fp0: particle field at the previous state, with the same layout as Fp.

  • particles: particle container.

  • ghost_1, ghost_2, ghost_3: whether F includes ghost nodes in each coordinate direction. Disable a keyword for a physical-only direction.

source
JustPIC.particle2centroid_flip! Function
julia
particle2centroid_flip!(F, Fp, Fp0, particles; ghost_1 = true, ghost_2 = true, ghost_3 = true)

Add the interpolated particle increment Fp - Fp0 to the cell centers F: F += Σ ω (Fp - Fp0) / Σ ω, with the weights of particle2centroid!.

F, Fp and Fp0 may be single fields or tuples of fields. Cells with no particles are left unchanged. See particle2grid_flip! for the arguments.

source