hypot
Returns sqrt(x * x + y * y), avoiding unnecessary overflow and underflow.
Special Cases:
| x | y | hypot |
|---|---|---|
| +-inf | any | +inf |
| any | +-inf | +inf |
| nan | fin | nan |
| fin | nan | nan |
Function parameters
Parameters
- x:anytype
- y:anytype
Returns sqrt(x * x + y * y), avoiding unnecessary overflow and underflow.
Functions
- hypot
- Returns sqrt(x * x + y * y), avoiding unnecessary overflow and underflow.
Source
Implementation
pub fn hypot(x: anytype, y: anytype) @TypeOf(x, y) {
const T = @TypeOf(x, y);
switch (@typeInfo(T)) {
.float => {},
.comptime_float => return @sqrt(x * x + y * y),
else => @compileError("hypot not implemented for " ++ @typeName(T)),
}
const lower = @sqrt(floatMin(T));
const upper = @sqrt(floatMax(T) / 2);
const incre = @sqrt(floatEps(T) / 2);
const scale = floatEpsAt(T, incre);
const hypfn = if (emulateFma(T)) hypotUnfused else hypotFused;
var major: T = x;
var minor: T = y;
if (isInf(major) or isInf(minor)) return inf(T);
if (isNan(major) or isNan(minor)) return nan(T);
if (T == f16) return @floatCast(@sqrt(@mulAdd(f32, x, x, @as(f32, y) * y)));
if (T == f32) return @floatCast(@sqrt(@mulAdd(f64, x, x, @as(f64, y) * y)));
major = @abs(major);
minor = @abs(minor);
if (minor > major) {
const tempo = major;
major = minor;
minor = tempo;
}
if (major * incre >= minor) return major;
if (major > upper) return hypfn(T, major * scale, minor * scale) / scale;
if (minor < lower) return hypfn(T, major / scale, minor / scale) * scale;
return hypfn(T, major, minor);
}