Advanced Examples
CLI Examples
Section titled “CLI Examples”Examples of more advanced Lua usage patterns, including custom operators for in-plan mutation and lightweight diagnostics.
1) Parameter sweep custom operator
Section titled “1) Parameter sweep custom operator”Use a Lua-defined operator to sweep the wavenumber of an existing stimulus over time. This keeps the mutation inside the execution plan instead of trying to reconfigure operators from an observation callback.
local N = 768local dt = 0.03local ctx = ooc.create()
ooc.set_timestep(ctx, dt)
local carrier = ooc.add_field(ctx, {N}, { type = "complex_double", fill = {0.0, 0.0}})
local modulator = ooc.add_field(ctx, {N}, { type = "complex_double", fill = {0.0, 0.0}})
ooc.add_zero_field_operator(ctx, carrier)
local stim_mod_sine = ooc.add_stimulus_operator(ctx, modulator, { type = "stimulus_sine", amplitude = 0.41, wavenumber = 1.0, omega = -0.42, rotation = math.pi / 2})
local stim_mod_lines = ooc.add_stimulus_operator(ctx, modulator, { type = "stimulus_spectral_lines", amplitude = 0.19, wavenumber = 1.0, omega = 0.01, phase = 4.8, harmonic_power = 0.94, harmonic_count = 2})
ooc.add_stimulus_operator(ctx, carrier, { type = "stimulus_sine", amplitude = 1.0, wavenumber = 1.0, omega = -0.51, phase = 0.36, spacing_x = 0.14})
ooc.add_mixer_operator(ctx, modulator, carrier, carrier, { mode = "pm", lhs_gain = 1.0, rhs_gain = 1.8, bias = 0.58})
local integrator = ooc.create_context_integrator(ctx, "rkf45", { initial_dt = dt})ooc.set_integrator(ctx, integrator)
local tick = 0local sweep_rate = 0.0005
ooc.add_operator(ctx, "sweep_op", function(context) tick = tick + 1 local sweep = math.sin(tick * sweep_rate)
ooc.operator_param_set(context, stim_mod_sine, "wavenumber", sweep) ooc.operator_param_set(context, stim_mod_lines, "wavenumber", sweep)
return trueend)
return ctx2) Lua-defined diagnostics operator
Section titled “2) Lua-defined diagnostics operator”Defines a custom operator that logs the most recent step metrics every 50 ticks while the simulation is running.
local ctx = ooc.create()local dt = 0.02
ooc.set_timestep(ctx, dt)
local field = ooc.add_field(ctx, {256}, { type = "real_double", fill = 0.0})
ooc.add_stimulus_operator(ctx, field, { type = "stimulus_sine", amplitude = 0.2, wavenumber = 0.5, omega = 0.15, scale_by_dt = true})
local integrator = ooc.create_context_integrator(ctx, "rk4", { initial_dt = dt})ooc.set_integrator(ctx, integrator)
local tick = 0
ooc.add_operator(ctx, "tick_counter", function(context) tick = tick + 1
if tick % 50 == 0 then local metrics = ooc.step_metrics_latest(context) if metrics then ooc.log("step=%d dt=%.6f accepted=%s dirty=%d", tick, metrics.accepted_dt, tostring(metrics.accepted), metrics.dirty_writes) end end
return trueend)
return ctx