1use std::ops;
4
5use super::{StringExtT, StringT};
6use crate::impl_for_shared_ref;
7
8static HEX_CHARS_LOWER: [u8; 16] = [
10 b'0', b'1', b'2', b'3', b'4', b'5', b'6', b'7', b'8', b'9', b'a', b'b', b'c', b'd', b'e', b'f',
11];
12
13static HEX_CHARS_UPPER: [u8; 16] = [
15 b'0', b'1', b'2', b'3', b'4', b'5', b'6', b'7', b'8', b'9', b'A', b'B', b'C', b'D', b'E', b'F',
16];
17
18#[derive(Debug, Clone, Copy, PartialEq, PartialOrd, Eq, Ord)]
21#[repr(transparent)]
22pub struct NumStr<
44 const B: u8 = 10,
45 const U: bool = false,
46 const R: usize = 0,
47 const M: usize = 0,
48 T = usize,
49>(T);
50
51impl<const B: u8, const U: bool, const R: usize, const M: usize, T> AsRef<T>
52 for NumStr<B, U, R, M, T>
53{
54 #[inline]
55 fn as_ref(&self) -> &T {
56 &self.0
57 }
58}
59
60impl<const B: u8, const U: bool, const R: usize, const M: usize, T> ops::Deref
61 for NumStr<B, U, R, M, T>
62{
63 type Target = T;
64
65 fn deref(&self) -> &Self::Target {
66 &self.0
67 }
68}
69
70impl<const B: u8, const U: bool, const R: usize, const M: usize, T> ops::DerefMut
71 for NumStr<B, U, R, M, T>
72{
73 fn deref_mut(&mut self) -> &mut Self::Target {
74 &mut self.0
75 }
76}
77
78impl<T> NumStr<10, false, 0, 0, T> {
79 #[inline]
80 pub fn new_default(inner: T) -> Self {
106 NumStr(inner)
107 }
108
109 #[inline]
110 pub fn hex_default(inner: T) -> NumStr<16, false, 0, 0, T> {
134 NumStr(inner)
135 }
136}
137
138impl NumStr<10, false, 0, 0, u8> {
139 #[inline]
140 pub fn hex_byte_default(inner: u8) -> NumStr<16, false, 2, 0, u8> {
166 NumStr(inner)
167 }
168}
169
170impl<const B: u8, const U: bool, const R: usize, const M: usize, T> NumStr<B, U, R, M, T> {
171 #[inline]
172 pub fn new(inner: T) -> Self {
174 NumStr(inner)
175 }
176
177 #[inline]
178 pub fn decimal(self) -> NumStr<10, U, R, M, T> {
180 NumStr(self.0)
181 }
182
183 #[inline]
184 pub fn hexadecimal(self) -> NumStr<16, U, R, M, T> {
186 NumStr(self.0)
187 }
188
189 #[inline]
190 pub fn set_custom_base<const NB: u8>(self) -> NumStr<NB, U, R, M, T> {
194 debug_assert!(NB >= 2 && NB <= 16);
195
196 NumStr(self.0)
197 }
198
199 #[inline]
200 pub fn set_uppercase<const NU: bool>(self) -> NumStr<B, NU, R, M, T> {
206 NumStr(self.0)
207 }
208
209 #[inline]
210 pub fn set_resize_len<const NR: usize>(self) -> NumStr<B, U, NR, M, T> {
219 NumStr(self.0)
220 }
221
222 #[inline]
223 pub fn set_minimum_len<const NM: usize>(self) -> NumStr<B, U, R, NM, T> {
231 NumStr(self.0)
232 }
233
234 #[inline]
235 fn charset() -> &'static [u8] {
236 debug_assert!(B >= 2 && B <= 16, "unsupported base: {}", B);
237
238 if U {
239 &HEX_CHARS_UPPER
240 } else {
241 &HEX_CHARS_LOWER
242 }
243 }
244}
245
246impl<const B: u8, const U: bool, const R: usize, const M: usize> NumStr<B, U, R, M, f32> {
247 #[inline]
248 pub fn set_integer_only<const NU: bool>(self) -> NumStr<B, NU, R, M, f32> {
252 NumStr(self.0)
253 }
254}
255
256impl<const B: u8, const U: bool, const R: usize, const M: usize> NumStr<B, U, R, M, f64> {
257 #[inline]
258 pub fn set_integer_only<const NU: bool>(self) -> NumStr<B, NU, R, M, f64> {
262 NumStr(self.0)
263 }
264}
265
266macro_rules! impl_num_str {
267 (UNSIGNED: $($ty:ty) +) => {
268 $(
269 impl<const B: u8, const U: bool, const R: usize, const M: usize> NumStr<B, U, R, M, $ty> {
270 #[inline]
271 pub fn encode(self, string: &mut Vec<u8>) {
273 let current_ptr = string.len();
274
275 if R > 0 {
276 string.resize(current_ptr + R, b'0');
277
278 let (mut num, charset) = if self.0 == 0 {
279 return
280 } else {
281 (self.0, Self::charset())
282 };
283
284 let string = &mut string[current_ptr..current_ptr + R];
285
286 let mut count = 0;
287
288 while let Some(s) = string.get_mut(count) {
289 *s = charset[(num % B as $ty) as usize];
290 num /= B as $ty;
291 count += 1;
292
293 if num <= 0 {
294 break
295 }
296 }
297
298 string
299 } else {
300 let (mut num, charset) = if self.0 == 0 {
301 string.push(b'0');
302 return
303 } else {
304 (self.0, Self::charset())
305 };
306
307 let mut count = 0;
308
309 while num > 0 {
310 count += 1;
311 string.push(charset[(num % B as $ty) as usize]);
312 num /= B as $ty;
313 }
314
315 while count < M {
317 count += 1;
318 string.push(b'0');
319 }
320
321 let final_ptr = string.len();
322 &mut string[current_ptr..final_ptr]
323 }.reverse();
324 }
325
326 #[inline]
327 pub fn encode_bytes(self, string: &mut bytes::BytesMut) {
329 let current_ptr = string.len();
330
331 if R > 0 {
332 string.resize(current_ptr + R, b'0');
333
334 let (mut num, charset) = if self.0 == 0 {
335 return
336 } else {
337 (self.0, Self::charset())
338 };
339
340 let string = &mut string[current_ptr..current_ptr + R];
341
342 let mut count = 0;
343
344 while let Some(s) = string.get_mut(count) {
345 *s = charset[(num % B as $ty) as usize];
346 num /= B as $ty;
347 count += 1;
348
349 if num <= 0 {
350 break
351 }
352 }
353
354 string
355 } else {
356 let (mut num, charset) = if self.0 == 0 {
357 string.extend(b"0");
358 return
359 } else {
360 (self.0, Self::charset())
361 };
362
363 let mut count = 0;
364
365 while num > 0 {
366 count += 1;
367 string.extend([charset[(num % B as $ty) as usize]]);
368 num /= B as $ty;
369 }
370
371 while count < M {
373 count += 1;
374 string.extend([b'0']);
375 }
376
377 let final_ptr = string.len();
378 &mut string[current_ptr..final_ptr]
379 }.reverse();
380 }
381 }
382
383 impl_num_str!(@INTERNAL $ty);
384 )+
385 };
386 (SIGNED: $($ty:ty as $uty:ty);+) => {
387 $(
388 impl<const B: u8, const U: bool, const R: usize, const M: usize> NumStr<B, U, R, M, $ty> {
389 #[inline]
390 pub fn encode(self, string: &mut Vec<u8>) {
392 if self.is_negative() {
393 string.push(b'-');
394 }
396
397 NumStr::<B, U, 0, 0, _>::new(self.0.unsigned_abs()).encode(string);
398 }
399
400 #[inline]
401 pub fn encode_bytes(self, string: &mut bytes::BytesMut) {
403 if self.is_negative() {
404 string.extend(b"-");
405 }
407
408 NumStr::<B, U, 0, 0, _>::new(self.0.unsigned_abs()).encode_bytes(string);
409 }
410 }
411
412 impl_num_str!(@INTERNAL $ty);
413 )+
414 };
415 (FLOAT: $($ty:ty) +) => {
416 $(
417 impl<const B: u8, const U: bool, const R: usize, const M: usize> NumStr<B, U, R, M, $ty> {
418 #[inline]
419 pub fn encode(mut self, string: &mut Vec<u8>) {
421 if U {
422 self.0 = self.0.trunc();
423 }
424
425 let original_len = string.len();
426
427 #[cfg(not(feature = "feat-string-ext-ryu"))]
428 string.extend(format!("{}", self.0).as_bytes());
429
430 #[cfg(feature = "feat-string-ext-ryu")]
431 string.extend(ryu::Buffer::new().format(self.0).as_bytes());
432
433 #[allow(unsafe_code)]
434 match unsafe { std::str::from_utf8_unchecked(string) }.rfind('.') {
435 Some(dot_pos) if self.0.is_finite() => {
436 if U {
437 string.truncate(dot_pos);
438 } else if R > 0 {
439 string.resize(dot_pos + R + 1, b'0');
440 } else if dot_pos - original_len < M {
441 string.resize(dot_pos + M + 1, b'0');
442 } else {
443 }
445 },
446 Some(_) => {
447 },
449 None if (U || !self.0.is_finite()) => {
450 },
452 None => {
453 string.push(b'.');
454 if R > 0 {
455 string.resize(original_len + R + 1, b'0');
456 } else if M > 0 {
457 string.resize(original_len + M + 1, b'0');
458 } else {
459 string.push(b'0');
460 }
461 }
462 }
463 }
464
465 #[inline]
466 pub fn encode_bytes(mut self, string: &mut bytes::BytesMut) {
468 if U {
469 self.0 = self.0.trunc();
470 }
471
472 let original_len = string.len();
473
474 #[cfg(not(feature = "feat-string-ext-ryu"))]
475 string.extend(format!("{}", self.0).as_bytes());
476
477 #[cfg(feature = "feat-string-ext-ryu")]
478 string.extend(ryu::Buffer::new().format(self.0).as_bytes());
479
480 #[allow(unsafe_code)]
481 match unsafe { std::str::from_utf8_unchecked(string) }.rfind('.') {
482 Some(dot_pos) if self.0.is_finite() => {
483 if U {
484 string.truncate(dot_pos);
485 } else if R > 0 {
486 string.resize(dot_pos + R + 1, b'0');
487 } else if dot_pos - original_len < M {
488 string.resize(dot_pos + M + 1, b'0');
489 } else {
490 }
492 },
493 Some(_) => {
494 },
496 None if (U || !self.0.is_finite()) => {
497 },
499 None => {
500 string.extend(b".");
501 if R > 0 {
502 string.resize(original_len + R + 1, b'0');
503 } else if M > 0 {
504 string.resize(original_len + M + 1, b'0');
505 } else {
506 string.extend(b"0");
507 }
508 }
509 }
510 }
511 }
512
513 impl_num_str!(@INTERNAL $ty);
514 )*
515 };
516
517 (@INTERNAL $ty:ty) => {
518 impl<const B: u8, const U: bool, const R: usize, const M: usize> StringT for NumStr<B, U, R, M, $ty> {
519 #[inline]
520 fn encode_to_buf(self, string: &mut Vec<u8>) {
521 self.encode(string)
522 }
523
524 #[inline]
525 fn encode_to_buf_with_separator(self, string: &mut Vec<u8>, separator: &str) {
526 self.encode(string);
527 string.extend(separator.as_bytes());
528 }
529
530 #[inline]
531 fn encode_to_bytes_buf(self, string: &mut bytes::BytesMut) {
532 self.encode_bytes(string)
533 }
534
535 #[inline]
536 fn encode_to_bytes_buf_with_separator(self, string: &mut bytes::BytesMut, separator: &str) {
537 self.encode_bytes(string);
538 string.extend(separator.as_bytes());
539 }
540 }
541
542 impl<const B: u8, const U: bool, const R: usize, const M: usize> StringExtT for NumStr<B, U, R, M, $ty> {}
543
544 impl StringT for $ty {
545 #[inline]
546 fn encode_to_buf(self, string: &mut Vec<u8>) {
547 NumStr::new_default(self).encode_to_buf(string)
548 }
549
550 #[inline]
551 fn encode_to_buf_with_separator(self, string: &mut Vec<u8>, separator: &str) {
552 NumStr::new_default(self).encode_to_buf_with_separator(string, separator)
553 }
554
555 #[inline]
556 fn encode_to_bytes_buf(self, string: &mut bytes::BytesMut) {
557 NumStr::new_default(self).encode_to_bytes_buf(string)
558 }
559
560 #[inline]
561 fn encode_to_bytes_buf_with_separator(self, string: &mut bytes::BytesMut, separator: &str) {
562 NumStr::new_default(self).encode_to_bytes_buf_with_separator(string, separator)
563 }
564 }
565
566 impl StringExtT for $ty {}
567 };
568}
569
570impl_num_str!(UNSIGNED: u8 u16 u32 u64 u128 usize);
571impl_num_str!(SIGNED: i8 as u8; i16 as u16; i32 as u32; i64 as u64; i128 as u128; isize as usize);
572impl_num_str!(FLOAT: f32 f64);
573impl_for_shared_ref!(COPIED: u8 u16 u32 u64 u128 usize i8 i16 i32 i64 i128 isize f32 f64);
574
575#[cfg(test)]
576#[allow(clippy::cognitive_complexity)]
577mod test {
578 use crate::string::{NumStr, StringExtT};
579
580 #[test]
581 fn test_num_basic() {
582 assert_eq!("0", (0_u8).to_string_ext());
584 assert_eq!("1", (1_u8).to_string_ext());
585 assert_eq!("123", (123_u8).to_string_ext());
586 assert_eq!(u8::MAX.to_string(), (u8::MAX).to_string_ext());
587
588 assert_eq!("0", (0_u16).to_string_ext());
589 assert_eq!("1", (1_u16).to_string_ext());
590 assert_eq!("123", (123_u16).to_string_ext());
591 assert_eq!(u16::MAX.to_string(), (u16::MAX).to_string_ext());
592
593 assert_eq!("0", (0_u32).to_string_ext());
594 assert_eq!("1", (1_u32).to_string_ext());
595 assert_eq!("123", (123_u32).to_string_ext());
596 assert_eq!(u32::MAX.to_string(), (u32::MAX).to_string_ext());
597
598 assert_eq!("0", (0_u64).to_string_ext());
599 assert_eq!("1", (1_u64).to_string_ext());
600 assert_eq!("123", (123_u64).to_string_ext());
601 assert_eq!(u64::MAX.to_string(), (u64::MAX).to_string_ext());
602
603 assert_eq!("0", (0_u128).to_string_ext());
604 assert_eq!("1", (1_u128).to_string_ext());
605 assert_eq!("123", (123_u128).to_string_ext());
606 assert_eq!(u128::MAX.to_string(), (u128::MAX).to_string_ext());
607
608 assert_eq!("0", (0_usize).to_string_ext());
609 assert_eq!("1", (1_usize).to_string_ext());
610 assert_eq!("123", (123_usize).to_string_ext());
611 assert_eq!(usize::MAX.to_string(), (usize::MAX).to_string_ext());
612
613 assert_eq!("-123", (-123_i8).to_string_ext());
615 assert_eq!("-1", (-1_i8).to_string_ext());
616 assert_eq!("0", (0_i8).to_string_ext());
617 assert_eq!("1", (1_i8).to_string_ext());
618 assert_eq!("123", (123_i8).to_string_ext());
619 assert_eq!(i8::MAX.to_string(), (i8::MAX).to_string_ext());
620 assert_eq!(i8::MIN.to_string(), (i8::MIN).to_string_ext());
621
622 assert_eq!("-123", (-123_i16).to_string_ext());
623 assert_eq!("-1", (-1_i16).to_string_ext());
624 assert_eq!("0", (0_i16).to_string_ext());
625 assert_eq!("1", (1_i16).to_string_ext());
626 assert_eq!("123", (123_i16).to_string_ext());
627 assert_eq!(i16::MAX.to_string(), (i16::MAX).to_string_ext());
628 assert_eq!(i16::MIN.to_string(), (i16::MIN).to_string_ext());
629
630 assert_eq!("-123", (-123_i32).to_string_ext());
631 assert_eq!("-1", (-1_i32).to_string_ext());
632 assert_eq!("0", (0_i32).to_string_ext());
633 assert_eq!("1", (1_i32).to_string_ext());
634 assert_eq!("123", (123_i32).to_string_ext());
635 assert_eq!(i32::MAX.to_string(), (i32::MAX).to_string_ext());
636 assert_eq!(i32::MIN.to_string(), (i32::MIN).to_string_ext());
637
638 assert_eq!("-123", (-123_i64).to_string_ext());
639 assert_eq!("-1", (-1_i64).to_string_ext());
640 assert_eq!("0", (0_i64).to_string_ext());
641 assert_eq!("1", (1_i64).to_string_ext());
642 assert_eq!("123", (123_i64).to_string_ext());
643 assert_eq!(i64::MAX.to_string(), (i64::MAX).to_string_ext());
644 assert_eq!(i64::MIN.to_string(), (i64::MIN).to_string_ext());
645
646 assert_eq!("-123", (-123_i128).to_string_ext());
647 assert_eq!("-1", (-1_i128).to_string_ext());
648 assert_eq!("0", (0_i128).to_string_ext());
649 assert_eq!("1", (1_i128).to_string_ext());
650 assert_eq!("123", (123_i128).to_string_ext());
651 assert_eq!(i128::MAX.to_string(), (i128::MAX).to_string_ext());
652 assert_eq!(i128::MIN.to_string(), (i128::MIN).to_string_ext());
653
654 assert_eq!("-123", (-123_isize).to_string_ext());
655 assert_eq!("-1", (-1_isize).to_string_ext());
656 assert_eq!("0", (0_isize).to_string_ext());
657 assert_eq!("1", (1_isize).to_string_ext());
658 assert_eq!("123", (123_isize).to_string_ext());
659 assert_eq!(isize::MAX.to_string(), (isize::MAX).to_string_ext());
660 assert_eq!(isize::MIN.to_string(), (isize::MIN).to_string_ext());
661
662 assert_eq!("-inf", f32::NEG_INFINITY.to_string_ext());
663 assert_eq!("-inf", f64::NEG_INFINITY.to_string_ext());
664 assert_eq!("-1.0", (-1.0_f32).to_string_ext());
665 assert_eq!("-1.0", (-1.0_f64).to_string_ext());
666 #[cfg(feature = "feat-string-ext-ryu")]
667 assert_eq!(
668 "-1.23e-40",
669 (-0.000000000000000000000000000000000000000123_f32).to_string_ext()
670 );
671 #[cfg(not(feature = "feat-string-ext-ryu"))]
672 assert_eq!(
673 "-0.000000000000000000000000000000000000000123",
674 (-0.000000000000000000000000000000000000000123_f32).to_string_ext()
675 );
676 #[cfg(feature = "feat-string-ext-ryu")]
677 assert_eq!(
678 "-1.23e-40",
679 (-0.000000000000000000000000000000000000000123_f64).to_string_ext()
680 );
681 #[cfg(not(feature = "feat-string-ext-ryu"))]
682 assert_eq!(
683 "-0.000000000000000000000000000000000000000123",
684 (-0.000000000000000000000000000000000000000123_f64).to_string_ext()
685 );
686 assert_eq!("-4.242", (-4.242_f32).to_string_ext());
687 assert_eq!("-4.242", (-4.242_f64).to_string_ext());
688 assert_eq!("0.0", (0.0_f32).to_string_ext());
689 assert_eq!("0.0", (0.0_f64).to_string_ext());
690 assert_eq!("1.0", (1.0_f32).to_string_ext());
691 assert_eq!("1.0", (1.0_f64).to_string_ext());
692 assert_eq!("4.242", (4.242_f32).to_string_ext());
693 assert_eq!("4.242", (4.242_f64).to_string_ext());
694 assert_eq!("inf", f32::INFINITY.to_string_ext());
695 assert_eq!("inf", f64::INFINITY.to_string_ext());
696 }
697
698 #[test]
699 fn test_num_hex() {
700 assert_eq!(
702 "0",
703 NumStr::new_default(0x0_u8).hexadecimal().to_string_ext()
704 );
705 assert_eq!(
706 "1",
707 NumStr::new_default(0x1_u8).hexadecimal().to_string_ext()
708 );
709 assert_eq!(
710 "42",
711 NumStr::new_default(0x42_u8).hexadecimal().to_string_ext()
712 );
713 assert_eq!(
714 "ff",
715 NumStr::new_default(u8::MAX).hexadecimal().to_string_ext()
716 );
717
718 assert_eq!(
719 "0",
720 NumStr::new_default(0x0_u16).hexadecimal().to_string_ext()
721 );
722 assert_eq!(
723 "1",
724 NumStr::new_default(0x1_u16).hexadecimal().to_string_ext()
725 );
726 assert_eq!(
727 "123",
728 NumStr::new_default(0x123_u16).hexadecimal().to_string_ext()
729 );
730 assert_eq!(
731 "ffff",
732 NumStr::new_default(u16::MAX).hexadecimal().to_string_ext()
733 );
734
735 assert_eq!(
736 "0",
737 NumStr::new_default(0x0_u32).hexadecimal().to_string_ext()
738 );
739 assert_eq!(
740 "1",
741 NumStr::new_default(0x1_u32).hexadecimal().to_string_ext()
742 );
743 assert_eq!(
744 "123",
745 NumStr::new_default(0x123_u32).hexadecimal().to_string_ext()
746 );
747 assert_eq!(
748 "ffffffff",
749 NumStr::new_default(u32::MAX).hexadecimal().to_string_ext()
750 );
751
752 assert_eq!(
753 "0",
754 NumStr::new_default(0x0_u64).hexadecimal().to_string_ext()
755 );
756 assert_eq!(
757 "1",
758 NumStr::new_default(0x1_u64).hexadecimal().to_string_ext()
759 );
760 assert_eq!(
761 "123",
762 NumStr::new_default(0x123_u64).hexadecimal().to_string_ext()
763 );
764 assert_eq!(
765 "ffffffffffffffff",
766 NumStr::new_default(u64::MAX).hexadecimal().to_string_ext()
767 );
768
769 assert_eq!(
770 "0",
771 NumStr::new_default(0x0_u128).hexadecimal().to_string_ext()
772 );
773 assert_eq!(
774 "1",
775 NumStr::new_default(0x1_u128).hexadecimal().to_string_ext()
776 );
777 assert_eq!(
778 "123",
779 NumStr::new_default(0x123_u128)
780 .hexadecimal()
781 .to_string_ext()
782 );
783 assert_eq!(
784 "ffffffffffffffffffffffffffffffff",
785 NumStr::new_default(u128::MAX).hexadecimal().to_string_ext()
786 );
787
788 assert_eq!(
789 "0",
790 NumStr::new_default(0x0_usize).hexadecimal().to_string_ext()
791 );
792 assert_eq!(
793 "1",
794 NumStr::new_default(0x1_usize).hexadecimal().to_string_ext()
795 );
796 assert_eq!(
797 "123",
798 NumStr::new_default(0x123_usize)
799 .hexadecimal()
800 .to_string_ext()
801 );
802 assert_eq!(
803 format!("{:x}", usize::MAX),
804 NumStr::new_default(usize::MAX)
805 .hexadecimal()
806 .to_string_ext()
807 );
808
809 assert_eq!(
811 "-42",
812 NumStr::new_default(-0x42_i8).hexadecimal().to_string_ext()
813 );
814 assert_eq!(
815 "-1",
816 NumStr::new_default(-0x1_i8).hexadecimal().to_string_ext()
817 );
818 assert_eq!(
819 "0",
820 NumStr::new_default(0x0_i8).hexadecimal().to_string_ext()
821 );
822 assert_eq!(
823 "1",
824 NumStr::new_default(0x1_i8).hexadecimal().to_string_ext()
825 );
826 assert_eq!(
827 "42",
828 NumStr::new_default(0x42_i8).hexadecimal().to_string_ext()
829 );
830 assert_eq!(
831 "7f",
832 NumStr::new_default(i8::MAX).hexadecimal().to_string_ext()
833 );
834 assert_eq!(
835 "-80",
836 NumStr::new_default(i8::MIN).hexadecimal().to_string_ext()
837 );
838
839 assert_eq!(
840 "-123",
841 NumStr::new_default(-0x123_i16)
842 .hexadecimal()
843 .to_string_ext()
844 );
845 assert_eq!(
846 "-1",
847 NumStr::new_default(-0x1_i16).hexadecimal().to_string_ext()
848 );
849 assert_eq!(
850 "0",
851 NumStr::new_default(0x0_i16).hexadecimal().to_string_ext()
852 );
853 assert_eq!(
854 "1",
855 NumStr::new_default(0x1_i16).hexadecimal().to_string_ext()
856 );
857 assert_eq!(
858 "123",
859 NumStr::new_default(0x123_i16).hexadecimal().to_string_ext()
860 );
861 assert_eq!(
862 "7fff",
863 NumStr::new_default(i16::MAX).hexadecimal().to_string_ext()
864 );
865 assert_eq!(
866 "-8000",
867 NumStr::new_default(i16::MIN).hexadecimal().to_string_ext()
868 );
869
870 assert_eq!(
871 "-123",
872 NumStr::new_default(-0x123_i32)
873 .hexadecimal()
874 .to_string_ext()
875 );
876 assert_eq!(
877 "-1",
878 NumStr::new_default(-0x1_i32).hexadecimal().to_string_ext()
879 );
880 assert_eq!(
881 "0",
882 NumStr::new_default(0x0_i32).hexadecimal().to_string_ext()
883 );
884 assert_eq!(
885 "1",
886 NumStr::new_default(0x1_i32).hexadecimal().to_string_ext()
887 );
888 assert_eq!(
889 "123",
890 NumStr::new_default(0x123_i32).hexadecimal().to_string_ext()
891 );
892 assert_eq!(
893 "7fffffff",
894 NumStr::new_default(i32::MAX).hexadecimal().to_string_ext()
895 );
896 assert_eq!(
897 "-80000000",
898 NumStr::new_default(i32::MIN).hexadecimal().to_string_ext()
899 );
900
901 assert_eq!(
902 "-123",
903 NumStr::new_default(-0x123_i64)
904 .hexadecimal()
905 .to_string_ext()
906 );
907 assert_eq!(
908 "-1",
909 NumStr::new_default(-0x1_i64).hexadecimal().to_string_ext()
910 );
911 assert_eq!(
912 "0",
913 NumStr::new_default(0x0_i64).hexadecimal().to_string_ext()
914 );
915 assert_eq!(
916 "1",
917 NumStr::new_default(0x1_i64).hexadecimal().to_string_ext()
918 );
919 assert_eq!(
920 "123",
921 NumStr::new_default(0x123_i64).hexadecimal().to_string_ext()
922 );
923 assert_eq!(
924 "7fffffffffffffff",
925 NumStr::new_default(i64::MAX).hexadecimal().to_string_ext()
926 );
927 assert_eq!(
928 "-8000000000000000",
929 NumStr::new_default(i64::MIN).hexadecimal().to_string_ext()
930 );
931
932 assert_eq!(
933 "-123",
934 NumStr::new_default(-0x123_i128)
935 .hexadecimal()
936 .to_string_ext()
937 );
938 assert_eq!(
939 "-1",
940 NumStr::new_default(-0x1_i128).hexadecimal().to_string_ext()
941 );
942 assert_eq!(
943 "0",
944 NumStr::new_default(0x0_i128).hexadecimal().to_string_ext()
945 );
946 assert_eq!(
947 "1",
948 NumStr::new_default(0x1_i128).hexadecimal().to_string_ext()
949 );
950 assert_eq!(
951 "123",
952 NumStr::new_default(0x123_i128)
953 .hexadecimal()
954 .to_string_ext()
955 );
956 assert_eq!(
957 "7fffffffffffffffffffffffffffffff",
958 NumStr::new_default(i128::MAX).hexadecimal().to_string_ext()
959 );
960 assert_eq!(
961 "-80000000000000000000000000000000",
962 NumStr::new_default(i128::MIN).hexadecimal().to_string_ext()
963 );
964
965 assert_eq!(
966 "-123",
967 NumStr::new_default(-0x123_isize)
968 .hexadecimal()
969 .to_string_ext()
970 );
971 assert_eq!(
972 "-1",
973 NumStr::new_default(-0x1_isize)
974 .hexadecimal()
975 .to_string_ext()
976 );
977 assert_eq!(
978 "0",
979 NumStr::new_default(0x0_isize).hexadecimal().to_string_ext()
980 );
981 assert_eq!(
982 "1",
983 NumStr::new_default(0x1_isize).hexadecimal().to_string_ext()
984 );
985 assert_eq!(
986 "123",
987 NumStr::new_default(0x123_isize)
988 .hexadecimal()
989 .to_string_ext()
990 );
991 assert_eq!(
992 format!("{:x}", isize::MAX),
993 NumStr::new_default(isize::MAX)
994 .hexadecimal()
995 .to_string_ext()
996 );
997 assert_eq!(
998 format!("-{:x}", isize::MIN),
999 NumStr::new_default(isize::MIN)
1000 .hexadecimal()
1001 .to_string_ext()
1002 );
1003 }
1004
1005 #[test]
1006 fn test_r_m() {
1007 let data = NumStr::new_default(123_456_789_usize);
1008
1009 assert_eq!(data.set_resize_len::<12>().to_string_ext(), "000123456789");
1010 assert_eq!(data.set_minimum_len::<12>().to_string_ext(), "000123456789");
1011 assert_eq!(data.set_resize_len::<9>().to_string_ext(), "123456789");
1012 assert_eq!(data.set_minimum_len::<9>().to_string_ext(), "123456789");
1013 assert_eq!(data.set_resize_len::<6>().to_string_ext(), "456789");
1014 assert_eq!(data.set_minimum_len::<6>().to_string_ext(), "123456789");
1015
1016 let data = NumStr::new_default(0x123_456_789_usize).hexadecimal();
1017 assert_eq!(data.set_resize_len::<12>().to_string_ext(), "000123456789");
1018 assert_eq!(data.set_minimum_len::<12>().to_string_ext(), "000123456789");
1019 assert_eq!(data.set_resize_len::<9>().to_string_ext(), "123456789");
1020 assert_eq!(data.set_minimum_len::<9>().to_string_ext(), "123456789");
1021 assert_eq!(data.set_resize_len::<6>().to_string_ext(), "456789");
1022 assert_eq!(data.set_minimum_len::<6>().to_string_ext(), "123456789");
1023
1024 let data = NumStr::new_default(123456789.87654321_f64);
1025 assert_eq!(
1026 data.set_resize_len::<12>().to_string_ext(),
1027 "123456789.876543210000"
1028 );
1029 assert_eq!(
1030 data.set_minimum_len::<12>().to_string_ext(),
1031 "123456789.876543210000"
1032 );
1033 assert_eq!(
1034 data.set_resize_len::<8>().to_string_ext(),
1035 "123456789.87654321"
1036 );
1037 assert_eq!(
1038 data.set_minimum_len::<8>().to_string_ext(),
1039 "123456789.87654321"
1040 );
1041 assert_eq!(
1042 data.set_resize_len::<7>().to_string_ext(),
1043 "123456789.8765432"
1044 );
1045 assert_eq!(
1046 data.set_minimum_len::<7>().to_string_ext(),
1047 "123456789.87654321"
1048 );
1049 assert_eq!(data.set_resize_len::<1>().to_string_ext(), "123456789.8");
1050 assert_eq!(
1051 data.set_minimum_len::<1>().to_string_ext(),
1052 "123456789.87654321"
1053 );
1054 assert_eq!(data.set_integer_only::<true>().to_string_ext(), "123456789");
1055 }
1056
1057 #[test]
1058 fn test_hex_uppercase() {
1059 let data = NumStr::new_default(0x1_234_567_890_abc_usize).hexadecimal();
1060 assert_eq!(
1061 data.set_uppercase::<true>().to_string_ext(),
1062 "1234567890ABC"
1063 );
1064 assert_eq!(
1065 data.set_uppercase::<false>().to_string_ext(),
1066 "1234567890abc"
1067 );
1068 }
1069}