Ir al contenido

underwater.propagation.numerical

La referencia de la API se publica en inglés en los dos idiomas: se genera a partir de los docstrings del código, que son su texto original.

Numerical models of underwater sound propagation (range-independent ocean).

Three complementary numerical solvers for the acoustic field in a horizontally-stratified ocean waveguide, complementing the closed-form propagation loss of phonometry.underwater.propagation.closed_form:

  • normal_modes — the normal-mode expansion. Solves the depth-separated Sturm-Liouville eigenvalue problem by finite differences and assembles the propagation loss from the propagating modes.
  • ray_trace — ray tracing. Integrates the ray-trajectory equations through a sound-speed profile (Runge-Kutta), returning the ray paths and the travel time accumulated along each of them.
  • parabolic_equation — the standard (Tappert) parabolic equation, solved with the split-step Fourier algorithm, returning the propagation-loss field.

All three are implemented clean-room from Jensen, Kuperman, Porter & Schmidt, Computational Ocean Acoustics (2nd ed., Springer 2011): the modal derivation (Ch. 5, Eqs. 5.3-5.17), the ray equations (Ch. 3, Eqs. 3.23-3.24) and the split-step Fourier PE (Ch. 6). They are validated against analytic oracles: the ideal (pressure-release) waveguide’s exact modes, the circular-arc ray paths of a linear sound-speed gradient together with the closed-form travel time along them (Medwin & Clay, Fundamentals of Acoustical Oceanography, Academic Press 1998, Eq. (3.3.20)), and mutual agreement of the PE and normal-mode propagation loss for a range-independent waveguide.

Densities are in kg/m3, sound speeds in m/s, depths and ranges in metres, frequencies in Hz. The water column has a pressure-release surface at z = 0.

Auto-generated from the source docstrings by scripts/generate_api_docs.py (make api-docs). Do not edit by hand.

normal_modes(
frequency_hz: float,
depths: NDArray[np.float64] | list[float],
sound_speeds: NDArray[np.float64] | list[float],
*,
source_depth: float,
receiver_depth: float,
ranges_m: NDArray[np.float64] | list[float] | None = None,
density: float = 1000.0,
bottom: str = 'pressure-release',
n_depth_points: int | None = None,
) -> NormalModeResult

Normal-mode propagation loss for a range-independent waveguide.

Solves the depth-separated Sturm-Liouville problem (Jensen Eq. 5.3) on a uniform finite-difference grid, then assembles the coherent propagation loss from the propagating modes (Eq. 5.17).

The finite-difference eigenvalues carry an error that grows with the mode’s vertical wavenumber, so near-cutoff modes need a fine grid. Two guards apply: eigenvalues inside the scheme’s error band () are discarded as numerically indistinguishable from cutoff, and a PhonometryWarning is emitted when a retained mode sits within ten times that band (increase n_depth_points to resolve it).

Parameters

NameDescription
frequency_hzSource frequency, in Hz.
depthsDepth samples of the sound-speed profile, in metres, starting at the surface z = 0 and strictly increasing to the bottom.
sound_speedsSound speed at each depth, in m/s.
source_depthSource depth zs, in metres.
receiver_depthReceiver depth for the propagation-loss slice, in m.
ranges_mRanges at which to evaluate the loss, in metres; defaults to 100 m to 10 km.
densityWater density (constant), in kg/m3.
bottom"pressure-release" (default) or "rigid".
n_depth_pointsNumber of finite-difference depth points. Default (None): derived from the physics as , which keeps the near-cutoff eigenvalue error small at any frequency/depth combination, capped at 20 000 points (very high products exceed the cap; the near-cutoff warning then indicates whether the capped grid suffices, and an explicit n_depth_points overrides the cap).

Returns: A NormalModeResult.

Raises

ExceptionWhen
ValueErrorIf the inputs are invalid.
NormalModeResult(
frequency: float,
wavenumbers: NDArray[np.float64],
mode_depths: NDArray[np.float64],
mode_functions: NDArray[np.float64],
ranges: NDArray[np.float64],
propagation_loss: NDArray[np.float64],
receiver_depth: float,
source_depth: float,
)

Normal-mode solution of a range-independent waveguide.

Attributes

NameDescription
frequencySource frequency, in Hz.
wavenumbersHorizontal wavenumbers krm of the propagating modes, in rad/m (descending order).
mode_depthsDepth grid of the mode functions, in metres.
mode_functionsOrthonormalised mode shapes Ψm(z), shape (n_modes, n_depths).
rangesRanges at which the propagation loss is evaluated, in metres.
propagation_lossCoherent propagation loss at receiver_depth per range, in dB.
receiver_depthReceiver depth of the propagation-loss slice, in m.
source_depthSource depth, in metres.
NormalModeResult.plot(
ax: Axes | None = None,
*,
language: str = 'en',
**kwargs: Any,
) -> Axes

Plot the propagation loss versus range (loss increasing downward).

parabolic_equation(
frequency_hz: float,
depths: NDArray[np.float64] | list[float],
sound_speeds: NDArray[np.float64] | list[float],
*,
source_depth: float,
max_range: float = 10000.0,
range_step: float = 10.0,
n_depth_points: int = 1024,
) -> ParabolicEquationResult

Propagation-loss field from the standard (Tappert) parabolic equation.

Marches the split-step Fourier solution (Jensen Ch. 6) in range with a discrete sine transform in depth, enforcing a pressure-release surface at z = 0 and bottom at z = water_depth. The envelope is related to pressure by and (Eqs. 6.70-6.71), using a Gaussian starter.

The standard PE is paraxial: it is accurate for propagation within roughly ±15-20° of the horizontal (Jensen §6.2). Steep modes therefore carry a phase error that shows at short and intermediate range in shallow-waveguide problems (a few dB against the exact field below a few water depths of range), converging at long range; the free-field calibration itself is exact to ~1e-4 dB at the default range_step.

Parameters

NameDescription
frequency_hzSource frequency, in Hz.
depthsDepth samples of the profile, in metres, from z = 0.
sound_speedsSound speed at each depth, in m/s.
source_depthSource depth, in metres.
max_rangeMaximum range, in metres.
range_stepRange marching step , in metres.
n_depth_pointsNumber of depth points (interior sine-transform grid).

Returns: A ParabolicEquationResult.

Raises

ExceptionWhen
ValueErrorIf the inputs are invalid.
ParabolicEquationResult(
frequency: float,
ranges: NDArray[np.float64],
depths: NDArray[np.float64],
propagation_loss: NDArray[np.float64],
source_depth: float,
)

Parabolic-equation propagation-loss field.

Attributes

NameDescription
frequencySource frequency, in Hz.
rangesRange grid, in metres.
depthsDepth grid, in metres.
propagation_lossPropagation-loss field PL(z, r), in dB, shape (n_depths, n_ranges).
source_depthSource depth, in metres.
ParabolicEquationResult.plot(
ax: Axes | None = None,
*,
language: str = 'en',
**kwargs: Any,
) -> Axes

Plot the propagation-loss field (depth increasing downward).

ray_trace(
depths: NDArray[np.float64] | list[float],
sound_speeds: NDArray[np.float64] | list[float],
*,
source_depth: float,
launch_angles_deg: NDArray[np.float64] | list[float],
max_range: float = 10000.0,
n_steps: int = 2000,
) -> RayTraceResult

Trace acoustic rays through a range-independent sound-speed profile.

Integrates the ray-trajectory equations (Jensen Eqs. 3.23-3.24) with a fixed-step fourth-order Runge-Kutta scheme, reflecting at the pressure-release surface (z = 0) and the bottom (z = water_depth).

The travel time is a third state of that same Runge-Kutta step rather than a quadrature run over the finished path: with the range-invariant Snell parameter it obeys , so it is integrated with the very stages that place the ray and cannot drift from the geometry actually returned. This is the same ray core, and the same travel-time equation, as the atmospheric atmospheric_ray_paths (which reflects at the ground instead of at the sea surface). Reflections cost no time, so the accumulated time stays continuous across them.

Parameters

NameDescription
depthsDepth samples of the profile, in metres, from z = 0.
sound_speedsSound speed at each depth, in m/s.
source_depthSource depth, in metres.
launch_angles_degLaunch angles from the horizontal, in degrees (positive downward).
max_rangeMaximum horizontal range to trace, in metres.
n_stepsNumber of integration steps per ray.

Returns: A RayTraceResult.

Raises

ExceptionWhen
ValueErrorIf the inputs are invalid.
RayTraceResult(
launch_angles: NDArray[np.float64],
ranges: NDArray[np.float64],
depths: NDArray[np.float64],
travel_times: NDArray[np.float64],
source_depth: float,
water_depth: float,
)

Ray-tracing solution through a sound-speed profile.

Attributes

NameDescription
launch_anglesLaunch angles from the horizontal, in degrees.
rangesPer-ray horizontal ranges, in metres, shape (n_rays, n_steps).
depthsPer-ray depths, in metres, shape (n_rays, n_steps).
travel_timesPer-ray cumulative travel times, in seconds, shape (n_rays, n_steps) (zero at the source, increasing along the ray).
source_depthSource depth, in metres.
water_depthWater-column depth, in metres.
RayTraceResult.plot(
ax: Axes | None = None,
*,
language: str = 'en',
**kwargs: Any,
) -> Axes

Plot the ray paths (depth increasing downward).