#[inline]
pub fn add3(a: [f64; 3], b: [f64; 3]) -> [f64; 3] {
[a[0] + b[0], a[1] + b[1], a[2] + b[2]]
}
#[inline]
pub fn sub3(a: [f64; 3], b: [f64; 3]) -> [f64; 3] {
[a[0] - b[0], a[1] - b[1], a[2] - b[2]]
}
#[inline]
pub fn neg3(v: [f64; 3]) -> [f64; 3] {
[-v[0], -v[1], -v[2]]
}
#[inline]
pub fn scale3(v: [f64; 3], s: f64) -> [f64; 3] {
[v[0] * s, v[1] * s, v[2] * s]
}
#[inline]
pub fn dot3(a: [f64; 3], b: [f64; 3]) -> f64 {
a[0] * b[0] + a[1] * b[1] + a[2] * b[2]
}
#[inline]
pub fn dot3_ref(a: &[f64; 3], b: &[f64; 3]) -> f64 {
a[0] * b[0] + a[1] * b[1] + a[2] * b[2]
}
#[inline]
pub fn dot3_z_yx_ref(a: &[f64; 3], b: &[f64; 3]) -> f64 {
a[2] * b[2] + (a[1] * b[1] + a[0] * b[0])
}
#[inline]
pub fn dot3_fused_z_yx_ref(a: &[f64; 3], b: &[f64; 3]) -> f64 {
a[2].mul_add(b[2], a[1].mul_add(b[1], a[0] * b[0]))
}
#[inline]
pub fn norm3(v: [f64; 3]) -> f64 {
dot3(v, v).sqrt()
}
#[inline]
pub fn norm3_ref(v: &[f64; 3]) -> f64 {
dot3_ref(v, v).sqrt()
}
#[inline]
pub fn unit3(v: [f64; 3]) -> Option<[f64; 3]> {
match norm3(v) {
n if n > 0.0 => Some(scale3(v, 1.0 / n)),
_ => None,
}
}
#[inline]
pub fn unit3_ref_unchecked(v: &[f64; 3]) -> [f64; 3] {
let n = norm3_ref(v);
[v[0] / n, v[1] / n, v[2] / n]
}
#[inline]
pub fn cross3(a: [f64; 3], b: [f64; 3]) -> [f64; 3] {
[
a[1] * b[2] - a[2] * b[1],
a[2] * b[0] - a[0] * b[2],
a[0] * b[1] - a[1] * b[0],
]
}
#[inline]
pub fn cross3_ref(a: &[f64; 3], b: &[f64; 3]) -> [f64; 3] {
[
a[1] * b[2] - a[2] * b[1],
a[2] * b[0] - a[0] * b[2],
a[0] * b[1] - a[1] * b[0],
]
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn named_dot_orders_match_their_explicit_recipes() {
let a = [1.25, -2.5, 3.75];
let b = [-4.0, 5.5, -6.25];
assert_eq!(
dot3(a, b).to_bits(),
(a[0] * b[0] + a[1] * b[1] + a[2] * b[2]).to_bits()
);
assert_eq!(
dot3_z_yx_ref(&a, &b).to_bits(),
(a[2] * b[2] + (a[1] * b[1] + a[0] * b[0])).to_bits()
);
assert_eq!(
dot3_fused_z_yx_ref(&a, &b).to_bits(),
a[2].mul_add(b[2], a[1].mul_add(b[1], a[0] * b[0]))
.to_bits()
);
}
#[test]
fn unit3_zero_vector_returns_none() {
assert_eq!(unit3([0.0, 0.0, 0.0]), None);
}
}