#[derive(Debug, Clone, Copy, PartialEq)]
pub struct Ordf32(pub f32);
#[derive(Debug, Clone, Copy, PartialEq)]
pub struct Ordf64(pub f64);
impl Ord for Ordf32 {
#[inline]
fn cmp(&self, other: &Self) -> core::cmp::Ordering {
let mut left = self.0.to_bits() as i32;
let mut right = other.0.to_bits() as i32;
left ^= (((left >> 31) as u32) >> 1) as i32;
right ^= (((right >> 31) as u32) >> 1) as i32;
left.cmp(&right)
}
}
impl Ord for Ordf64 {
#[inline]
fn cmp(&self, other: &Self) -> core::cmp::Ordering {
let mut left = self.0.to_bits() as i64;
let mut right = other.0.to_bits() as i64;
left ^= (((left >> 63) as u64) >> 1) as i64;
right ^= (((right >> 63) as u64) >> 1) as i64;
left.cmp(&right)
}
}
impl Eq for Ordf64 {}
impl Eq for Ordf32 {}
impl PartialOrd for Ordf32 {
fn partial_cmp(&self, other: &Self) -> Option<core::cmp::Ordering> {
Some(self.cmp(other))
}
}
impl PartialOrd for Ordf64 {
fn partial_cmp(&self, other: &Self) -> Option<core::cmp::Ordering> {
Some(self.cmp(other))
}
}
impl core::fmt::Display for Ordf32 {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
self.0.fmt(f)
}
}
impl core::fmt::Display for Ordf64 {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
self.0.fmt(f)
}
}
pub trait FloatExt {
fn ceil(self) -> Self;
}
impl FloatExt for f32 {
fn ceil(self) -> Self {
let floored_towards_zero = (self as i32) as f32;
if self < 0.0 || floored_towards_zero == self {
floored_towards_zero
} else {
floored_towards_zero + 1.0
}
}
}
#[cfg(test)]
mod test {
use super::*;
#[test]
fn ceil32() {
assert_eq!((-1.1).ceil(), -1.0);
assert_eq!((-0.1).ceil(), 0.0);
assert_eq!((0.0).ceil(), 0.0);
assert_eq!((1.0).ceil(), 1.0);
assert_eq!((1.1).ceil(), 2.0);
assert_eq!((2.9).ceil(), 3.0);
}
}