//! This example builds similar functions where one deals with a Trivial static //! fraction that (by its parameters and number sizes) doesn't have any illegal //! values, and a NotTrivial one that has. This program's (--release) code can //! be viewed with `objudump -d --demangle` or similar. #![feature(associated_consts)] extern crate staticfraction; #[derive(Default)] struct TrivialDescription; impl staticfraction::StaticFractionDescription for TrivialDescription { const NUM_OFFSET: u32 = 0; const NUM_FACTOR: u32 = 1; const DENOM: u32 = 100; } /// For this type, every value is OK type Trivial = staticfraction::StaticFraction; #[derive(Default)] struct NotTrivialDescription; impl staticfraction::StaticFractionDescription for NotTrivialDescription { const NUM_OFFSET: u32 = 0; const NUM_FACTOR: u32 = 65536 * 2; const DENOM: u32 = 99; } /// For this type, only about half the values are valid type NotTrivial = staticfraction::StaticFraction; /// With release builds, this produces only a few bytes of machine code -- /// looks like it's really just returning the input value. #[inline(never)] fn should_be_small(raw: u16) -> Trivial { Trivial::new_from_stored_checked(raw).unwrap() } /// This needs to (and does) produce more complex code. I'd expect it to be /// checking the input against a constant (and, failing that), panicking. What /// it actually does with current nightlies is to run something through /// try_from, which IMO should be constant-propagatable, so there is room for /// enhancement here. #[inline(never)] fn should_be_checking(raw: u16) -> NotTrivial { NotTrivial::new_from_stored_checked(raw).unwrap() } fn main() { let tested = should_be_small(42); debug_assert!(tested != 1); let tested = should_be_checking(42); debug_assert!(tested != 1); }