Files
rocketry/src/engine/numerics.js
2026-03-03 16:43:30 +00:00

43 lines
1.4 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
// Numerical methods for transcendental equations
/**
* Bisection method — finds root of f in [lo, hi] within tolerance.
* Returns null if no sign change is found.
*/
export function bisect(f, lo, hi, tol = 1e-10, maxIter = 200) {
let flo = f(lo)
let fhi = f(hi)
if (!isFinite(flo) || !isFinite(fhi)) return null
if (flo * fhi > 0) return null // no sign change
for (let i = 0; i < maxIter; i++) {
const mid = (lo + hi) / 2
if ((hi - lo) / 2 < tol) return mid
const fmid = f(mid)
if (fmid === 0) return mid
if (flo * fmid < 0) { hi = mid; fhi = fmid }
else { lo = mid; flo = fmid }
}
return (lo + hi) / 2
}
/**
* Isentropic area-ratio function A/A* as a function of Mach M and gamma.
* A/A* = (1/M) * [(2/(γ+1)) * (1 + (γ-1)/2 * M²)]^((γ+1)/(2(γ-1)))
*/
export function areaRatioFromMach(M, gamma) {
const exp = (gamma + 1) / (2 * (gamma - 1))
const base = (2 / (gamma + 1)) * (1 + (gamma - 1) / 2 * M * M)
return (1 / M) * Math.pow(base, exp)
}
/**
* Solve Mach number from area ratio and gamma using bisection.
* supersonic=true searches M > 1, false searches M < 1.
* Returns null if unsolvable.
*/
export function machFromAreaRatio(eps, gamma, supersonic = true) {
const f = (M) => areaRatioFromMach(M, gamma) - eps
if (supersonic) return bisect(f, 1.0001, 200, 1e-9)
else return bisect(f, 0.0001, 0.9999, 1e-9)
}