Anforderungen  |   Konzepte  |   Entwurf  |   Entwicklung  |   Qualitätssicherung  |   Lebenszyklus  |   Steuerung
 
 
 
 


Quelle  impls.rs   Sprache: unbekannt

 
// This file is part of ICU4X. For terms of use, please see the file
// called LICENSE at the top level of the ICU4X source tree
// (online at: https://github.com/unicode-org/icu4x/blob/main/LICENSE ).

use crate::*;
use core::fmt;

macro_rules! impl_write_num {
    ($u:ty, $i:ty, $test:ident) => {
        impl $crate::Writeable for $u {
            fn write_to<W: core::fmt::Write + ?Sized>(&self, sink: &mut W) -> core::fmt::Result {
                const MAX_LEN: usize = <$u>::MAX.ilog10() as usize + 1;
                let mut buf = [b'0'; MAX_LEN];
                let mut n = *self;
                let mut i = MAX_LEN;
                #[allow(clippy::indexing_slicing)] // n < 10^i
                while n != 0 {
                    i -= 1;
                    buf[i] = b'0' + (n % 10) as u8;
                    n /= 10;
                }
                if i == MAX_LEN {
                    debug_assert_eq!(*self, 0);
                    i -= 1;
                }
                #[allow(clippy::indexing_slicing)] // buf is ASCII
                let s = unsafe { core::str::from_utf8_unchecked(&buf[i..]) };
                sink.write_str(s)
            }

            fn writeable_length_hint(&self) -> $crate::LengthHint {
                LengthHint::exact(self.checked_ilog10().unwrap_or(0) as usize + 1)
            }
        }

        impl $crate::Writeable for $i {
            fn write_to<W: core::fmt::Write + ?Sized>(&self, sink: &mut W) -> core::fmt::Result {
                if self.is_negative() {
                    sink.write_str("-")?;
                }
                self.unsigned_abs().write_to(sink)
            }

            fn writeable_length_hint(&self) -> $crate::LengthHint {
                $crate::LengthHint::exact(if self.is_negative() { 1 } else { 0 })
                    + self.unsigned_abs().writeable_length_hint()
            }
        }

        #[test]
        fn $test() {
            use $crate::assert_writeable_eq;
            assert_writeable_eq!(&(0 as $u), "0");
            assert_writeable_eq!(&(0 as $i), "0");
            assert_writeable_eq!(&(-0 as $i), "0");
            assert_writeable_eq!(&(1 as $u), "1");
            assert_writeable_eq!(&(1 as $i), "1");
            assert_writeable_eq!(&(-1 as $i), "-1");
            assert_writeable_eq!(&(9 as $u), "9");
            assert_writeable_eq!(&(9 as $i), "9");
            assert_writeable_eq!(&(-9 as $i), "-9");
            assert_writeable_eq!(&(10 as $u), "10");
            assert_writeable_eq!(&(10 as $i), "10");
            assert_writeable_eq!(&(-10 as $i), "-10");
            assert_writeable_eq!(&(99 as $u), "99");
            assert_writeable_eq!(&(99 as $i), "99");
            assert_writeable_eq!(&(-99 as $i), "-99");
            assert_writeable_eq!(&(100 as $u), "100");
            assert_writeable_eq!(&(-100 as $i), "-100");
            assert_writeable_eq!(&<$u>::MAX, <$u>::MAX.to_string());
            assert_writeable_eq!(&<$i>::MAX, <$i>::MAX.to_string());
            assert_writeable_eq!(&<$i>::MIN, <$i>::MIN.to_string());

            use rand::{rngs::SmallRng, Rng, SeedableRng};
            let mut rng = SmallRng::seed_from_u64(4); // chosen by fair dice roll.
                                                      // guaranteed to be random.
            for _ in 0..1000 {
                let rand = rng.gen::<$u>();
                assert_writeable_eq!(rand, rand.to_string());
            }
        }
    };
}

impl_write_num!(u8, i8, test_u8);
impl_write_num!(u16, i16, test_u16);
impl_write_num!(u32, i32, test_u32);
impl_write_num!(u64, i64, test_u64);
impl_write_num!(u128, i128, test_u128);
impl_write_num!(usize, isize, test_usize);

impl Writeable for str {
    #[inline]
    fn write_to<W: fmt::Write + ?Sized>(&self, sink: &mut W) -> fmt::Result {
        sink.write_str(self)
    }

    #[inline]
    fn writeable_length_hint(&self) -> LengthHint {
        LengthHint::exact(self.len())
    }

    /// Returns a borrowed `str`.
    ///
    /// # Examples
    ///
    /// ```
    /// use std::borrow::Cow;
    /// use writeable::Writeable;
    ///
    /// let cow = "foo".write_to_string();
    /// assert!(matches!(cow, Cow::Borrowed(_)));
    /// ```
    #[inline]
    fn write_to_string(&self) -> Cow<str> {
        Cow::Borrowed(self)
    }

    #[inline]
    fn writeable_cmp_bytes(&self, other: &[u8]) -> core::cmp::Ordering {
        self.as_bytes().cmp(other)
    }
}

impl Writeable for String {
    #[inline]
    fn write_to<W: fmt::Write + ?Sized>(&self, sink: &mut W) -> fmt::Result {
        sink.write_str(self)
    }

    #[inline]
    fn writeable_length_hint(&self) -> LengthHint {
        LengthHint::exact(self.len())
    }

    #[inline]
    fn write_to_string(&self) -> Cow<str> {
        Cow::Borrowed(self)
    }

    #[inline]
    fn writeable_cmp_bytes(&self, other: &[u8]) -> core::cmp::Ordering {
        self.as_bytes().cmp(other)
    }
}

impl Writeable for char {
    #[inline]
    fn write_to<W: fmt::Write + ?Sized>(&self, sink: &mut W) -> fmt::Result {
        sink.write_char(*self)
    }

    #[inline]
    fn writeable_length_hint(&self) -> LengthHint {
        LengthHint::exact(self.len_utf8())
    }

    #[inline]
    fn write_to_string(&self) -> Cow<str> {
        let mut s = String::with_capacity(self.len_utf8());
        s.push(*self);
        Cow::Owned(s)
    }

    #[inline]
    fn writeable_cmp_bytes(&self, other: &[u8]) -> core::cmp::Ordering {
        self.encode_utf8(&mut [0u8; 4]).as_bytes().cmp(other)
    }
}

impl<T: Writeable + ?Sized> Writeable for &T {
    #[inline]
    fn write_to<W: fmt::Write + ?Sized>(&self, sink: &mut W) -> fmt::Result {
        (*self).write_to(sink)
    }

    #[inline]
    fn write_to_parts<W: PartsWrite + ?Sized>(&self, sink: &mut W) -> fmt::Result {
        (*self).write_to_parts(sink)
    }

    #[inline]
    fn writeable_length_hint(&self) -> LengthHint {
        (*self).writeable_length_hint()
    }

    #[inline]
    fn write_to_string(&self) -> Cow<str> {
        (*self).write_to_string()
    }

    #[inline]
    fn writeable_cmp_bytes(&self, other: &[u8]) -> core::cmp::Ordering {
        (*self).writeable_cmp_bytes(other)
    }
}

macro_rules! impl_write_smart_pointer {
    ($ty:path, T: $extra_bound:path) => {
        impl<'a, T: ?Sized + Writeable + $extra_bound> Writeable for $ty {
            #[inline]
            fn write_to<W: fmt::Write + ?Sized>(&self, sink: &mut W) -> fmt::Result {
                core::borrow::Borrow::<T>::borrow(self).write_to(sink)
            }
            #[inline]
            fn write_to_parts<W: PartsWrite + ?Sized>(&self, sink: &mut W) -> fmt::Result {
                core::borrow::Borrow::<T>::borrow(self).write_to_parts(sink)
            }
            #[inline]
            fn writeable_length_hint(&self) -> LengthHint {
                core::borrow::Borrow::<T>::borrow(self).writeable_length_hint()
            }
            #[inline]
            fn write_to_string(&self) -> Cow<str> {
                core::borrow::Borrow::<T>::borrow(self).write_to_string()
            }
            #[inline]
            fn writeable_cmp_bytes(&self, other: &[u8]) -> core::cmp::Ordering {
                core::borrow::Borrow::<T>::borrow(self).writeable_cmp_bytes(other)
            }
        }
    };
    ($ty:path) => {
        // Add a harmless duplicate Writeable bound
        impl_write_smart_pointer!($ty, T: Writeable);
    };
}

impl_write_smart_pointer!(Cow<'a, T>, T: alloc::borrow::ToOwned);
impl_write_smart_pointer!(alloc::boxed::Box<T>);
impl_write_smart_pointer!(alloc::rc::Rc<T>);
impl_write_smart_pointer!(alloc::sync::Arc<T>);

#[test]
fn test_string_impls() {
    fn check_writeable_slice<W: Writeable + core::fmt::Display>(writeables: &[W]) {
        assert_writeable_eq!(&writeables[0], "");
        assert_writeable_eq!(&writeables[1], "abc");
        assert!(matches!(writeables[0].write_to_string(), Cow::Borrowed(_)));
        assert!(matches!(writeables[1].write_to_string(), Cow::Borrowed(_)));
    }

    // test str impl
    let arr: &[&str] = &["", "abc"];
    check_writeable_slice(arr);

    // test String impl
    let arr: &[String] = &[String::new(), "abc".to_owned()];
    check_writeable_slice(arr);

    // test char impl
    let chars = ['a', 'β', '你', '��'];
    for i in 0..chars.len() {
        let s = String::from(chars[i]);
        assert_writeable_eq!(&chars[i], s);
        for j in 0..chars.len() {
            assert_eq!(
                chars[j].writeable_cmp_bytes(s.as_bytes()),
                chars[j].cmp(&chars[i]),
                "{:?} vs {:?}",
                chars[j],
                chars[i]
            );
        }
    }

    // test Cow impl
    let arr: &[Cow<str>] = &[Cow::Borrowed(""), Cow::Owned("abc".to_string())];
    check_writeable_slice(arr);

    // test Box impl
    let arr: &[Box<str>] = &["".into(), "abc".into()];
    check_writeable_slice(arr);

    // test Rc impl
    let arr: &[alloc::rc::Rc<str>] = &["".into(), "abc".into()];
    check_writeable_slice(arr);

    // test Arc impl
    let arr: &[alloc::sync::Arc<str>] = &["".into(), "abc".into()];
    check_writeable_slice(arr);

    // test &T impl
    let arr: &[&String] = &[&String::new(), &"abc".to_owned()];
    check_writeable_slice(arr);
}

[ Dauer der Verarbeitung: 0.22 Sekunden  (vorverarbeitet)  ]

                                                                                                                                                                                                                                                                                                                                                                                                     


Neuigkeiten

     Aktuelles
     Motto des Tages

Software

     Produkte
     Quellcodebibliothek

Aktivitäten

     Artikel über Sicherheit
     Anleitung zur Aktivierung von SSL

Muße

     Gedichte
     Musik
     Bilder

Jenseits des Üblichen ....

Besucherstatistik

Besucherstatistik

Monitoring

Montastic status badge