pub struct SO3 { /* private fields */ }Expand description
SO(3) group element - 3×3 real orthogonal matrix with determinant 1
Represents a rotation in 3D space.
§Representation
We use Matrix3<f64> from nalgebra to represent the 3×3 rotation matrix.
§Constraints
- Orthogonality: R^T R = I
- Determinant: det(R) = 1
§Examples
use lie_groups::so3::SO3;
use lie_groups::traits::LieGroup;
// Rotation around Z-axis by π/2
let rot = SO3::rotation_z(std::f64::consts::FRAC_PI_2);
// Verify it's orthogonal
assert!(rot.verify_orthogonality(1e-10));Implementations§
Source§impl SO3
impl SO3
Sourcepub fn rotation_x(angle: f64) -> Self
pub fn rotation_x(angle: f64) -> Self
Rotation around X-axis by angle θ (in radians)
R_x(θ) = [[1, 0, 0], [0, cos(θ), -sin(θ)], [0, sin(θ), cos(θ)]]Sourcepub fn rotation_y(angle: f64) -> Self
pub fn rotation_y(angle: f64) -> Self
Rotation around Y-axis by angle θ (in radians)
R_y(θ) = [[cos(θ), 0, sin(θ)], [0, 1, 0], [-sin(θ), 0, cos(θ)]]Sourcepub fn rotation_z(angle: f64) -> Self
pub fn rotation_z(angle: f64) -> Self
Rotation around Z-axis by angle θ (in radians)
R_z(θ) = [[cos(θ), -sin(θ), 0], [sin(θ), cos(θ), 0], [0, 0, 1]]Sourcepub fn rotation(axis: [f64; 3], angle: f64) -> Self
pub fn rotation(axis: [f64; 3], angle: f64) -> Self
Rotation around arbitrary axis by angle
Uses Rodrigues’ rotation formula:
R(θ, n̂) = I + sin(θ)[n̂]_× + (1-cos(θ))[n̂]_ײwhere [n̂]_× is the skew-symmetric matrix for axis n̂.
Sourcepub fn from_matrix(arr: [[f64; 3]; 3]) -> Self
pub fn from_matrix(arr: [[f64; 3]; 3]) -> Self
Create from 3×3 array format
§Panics
Does not verify orthogonality. Use verify_orthogonality() after construction.
Sourcepub fn verify_orthogonality(&self, tolerance: f64) -> bool
pub fn verify_orthogonality(&self, tolerance: f64) -> bool
Verify orthogonality: R^T R = I
Sourcepub fn distance_to_identity(&self) -> f64
pub fn distance_to_identity(&self) -> f64
Distance from identity (rotation angle)
For a rotation matrix R, the angle θ satisfies:
trace(R) = 1 + 2cos(θ)Sourcepub fn interpolate(&self, other: &Self, t: f64) -> Self
pub fn interpolate(&self, other: &Self, t: f64) -> Self
Interpolate between two SO(3) elements with proper orthogonalization
Uses linear interpolation of matrix elements followed by Gram-Schmidt orthogonalization to ensure the result stays on SO(3).
§Arguments
other- The target rotationt- Interpolation parameter in [0, 1]
§Returns
An SO(3) element: self at t=0, other at t=1
§Note
This is NOT geodesic interpolation (SLERP). For true geodesic paths, convert to quaternions and use quaternion SLERP. However, this method guarantees the result is always a valid rotation matrix.
Sourcepub fn gram_schmidt_orthogonalize(matrix: Matrix3<f64>) -> Self
pub fn gram_schmidt_orthogonalize(matrix: Matrix3<f64>) -> Self
Orthogonalize a matrix using Gram-Schmidt process
Takes a near-orthogonal matrix and projects it back onto SO(3). This is essential for numerical stability when matrices drift from orthogonality due to floating-point accumulation.
§Algorithm
- Normalize first column
- Orthogonalize and normalize second column
- Compute third column as cross product (ensures determinant = 1)
Sourcepub fn renormalize(&self) -> Self
pub fn renormalize(&self) -> Self
Re-normalize a rotation matrix that may have drifted
Use this periodically after many matrix multiplications to prevent numerical drift from accumulating.
Sourcepub fn geodesic_distance(&self, other: &Self) -> f64
pub fn geodesic_distance(&self, other: &Self) -> f64
Geodesic distance between two SO(3) elements
d(R₁, R₂) = ||log(R₁ᵀ R₂)||
This is the rotation angle of the relative rotation R₁ᵀ R₂.
Trait Implementations§
Source§impl LieGroup for SO3
impl LieGroup for SO3
Source§const MATRIX_DIM: usize = 3
const MATRIX_DIM: usize = 3
Source§type Algebra = So3Algebra
type Algebra = So3Algebra
Source§fn conjugate_transpose(&self) -> Self
fn conjugate_transpose(&self) -> Self
Source§fn adjoint_action(&self, algebra_element: &So3Algebra) -> So3Algebra
fn adjoint_action(&self, algebra_element: &So3Algebra) -> So3Algebra
Ad_g: 𝔤 → 𝔤 Read moreSource§fn distance_to_identity(&self) -> f64
fn distance_to_identity(&self) -> f64
Source§fn exp(tangent: &So3Algebra) -> Self
fn exp(tangent: &So3Algebra) -> Self
Source§fn log(&self) -> LogResult<So3Algebra>
fn log(&self) -> LogResult<So3Algebra>
Source§fn distance(&self, other: &Self) -> f64
fn distance(&self, other: &Self) -> f64
Source§fn is_near_identity(&self, tolerance: f64) -> bool
fn is_near_identity(&self, tolerance: f64) -> bool
Source§fn trace_identity() -> f64
fn trace_identity() -> f64
Source§fn reorthogonalize(&self) -> Self
fn reorthogonalize(&self) -> Self
Source§impl MulAssign<&SO3> for SO3
impl MulAssign<&SO3> for SO3
Source§fn mul_assign(&mut self, rhs: &SO3)
fn mul_assign(&mut self, rhs: &SO3)
*= operation. Read moreimpl Compact for SO3
SO(3) is compact
The rotation group is diffeomorphic to ℝP³ (real projective 3-space). All rotations are bounded: ||R|| = 1.
impl SemiSimple for SO3
SO(3) is semi-simple
impl Simple for SO3
SO(3) is simple
It has no non-trivial normal subgroups (for dimension > 2).
impl StructuralPartialEq for SO3
Auto Trait Implementations§
impl Freeze for SO3
impl RefUnwindSafe for SO3
impl Send for SO3
impl Sync for SO3
impl Unpin for SO3
impl UnsafeUnpin for SO3
impl UnwindSafe for SO3
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
Source§fn to_subset(&self) -> Option<SS>
fn to_subset(&self) -> Option<SS>
self from the equivalent element of its
superset. Read moreSource§fn is_in_subset(&self) -> bool
fn is_in_subset(&self) -> bool
self is actually part of its subset T (and can be converted to it).Source§fn to_subset_unchecked(&self) -> SS
fn to_subset_unchecked(&self) -> SS
self.to_subset but without any property checks. Always succeeds.Source§fn from_subset(element: &SS) -> SP
fn from_subset(element: &SS) -> SP
self to the equivalent element of its superset.