snarkvm_console_types_integers/
parse.rs1use super::*;
17
18impl<E: Environment, I: IntegerType> Parser for Integer<E, I> {
19 #[inline]
21 fn parse(string: &str) -> ParserResult<Self> {
22 let (string, negation) = map(opt(tag("-")), |neg: Option<&str>| neg.unwrap_or_default().to_string())(string)?;
24 let (string, primitive) = recognize(many1(terminated(one_of("0123456789"), many0(char('_')))))(string)?;
26 let primitive = negation + primitive;
28 let (string, value) = map_res(tag(Self::type_name()), |_| primitive.replace('_', "").parse())(string)?;
30
31 Ok((string, Integer::new(value)))
32 }
33}
34
35impl<E: Environment, I: IntegerType> FromStr for Integer<E, I> {
36 type Err = Error;
37
38 #[inline]
40 fn from_str(string: &str) -> Result<Self> {
41 match Self::parse(string) {
42 Ok((remainder, object)) => {
43 ensure!(remainder.is_empty(), "Failed to parse string. Found invalid character in: \"{remainder}\"");
45 Ok(object)
47 }
48 Err(error) => bail!("Failed to parse string. {error}"),
49 }
50 }
51}
52
53impl<E: Environment, I: IntegerType> Debug for Integer<E, I> {
54 fn fmt(&self, f: &mut Formatter) -> fmt::Result {
55 Display::fmt(self, f)
56 }
57}
58
59impl<E: Environment, I: IntegerType> Display for Integer<E, I> {
60 fn fmt(&self, f: &mut Formatter) -> fmt::Result {
61 write!(f, "{}{}", self.integer, Self::type_name())
62 }
63}
64
65#[cfg(test)]
66mod tests {
67 use super::*;
68 use snarkvm_console_network_environment::Console;
69
70 type CurrentEnvironment = Console;
71
72 const ITERATIONS: u64 = 10_000;
73
74 #[test]
75 fn test_parse() -> Result<()> {
76 let rng = &mut TestRng::default();
77
78 assert!(Integer::<CurrentEnvironment, i8>::parse(Integer::<CurrentEnvironment, i8>::type_name()).is_err());
80 assert!(Integer::<CurrentEnvironment, i8>::parse("").is_err());
81
82 for _ in 0..ITERATIONS {
83 let integer: i8 = Uniform::rand(rng);
85
86 let expected = format!("{}{}", integer, Integer::<CurrentEnvironment, i8>::type_name());
87 let (remainder, candidate) = Integer::<CurrentEnvironment, i8>::parse(&expected).unwrap();
88 assert_eq!(format!("{expected}"), candidate.to_string());
89 assert_eq!("", remainder);
90 }
91 Ok(())
92 }
93
94 #[test]
95 fn test_display() {
96 fn check_display<E: Environment, I: IntegerType>(rng: &mut TestRng) {
99 for _ in 0..ITERATIONS {
100 let element = Uniform::rand(rng);
101
102 let candidate = Integer::<E, I>::new(element);
103 assert_eq!(format!("{element}{}", Integer::<E, I>::type_name()), format!("{candidate}"));
104
105 let candidate_recovered = Integer::<E, I>::from_str(&format!("{candidate}")).unwrap();
106 assert_eq!(candidate, candidate_recovered);
107 }
108 }
109
110 let mut rng = TestRng::default();
111
112 check_display::<CurrentEnvironment, u8>(&mut rng);
113 check_display::<CurrentEnvironment, u16>(&mut rng);
114 check_display::<CurrentEnvironment, u32>(&mut rng);
115 check_display::<CurrentEnvironment, u64>(&mut rng);
116 check_display::<CurrentEnvironment, u128>(&mut rng);
117
118 check_display::<CurrentEnvironment, i8>(&mut rng);
119 check_display::<CurrentEnvironment, i16>(&mut rng);
120 check_display::<CurrentEnvironment, i32>(&mut rng);
121 check_display::<CurrentEnvironment, i64>(&mut rng);
122 check_display::<CurrentEnvironment, i128>(&mut rng);
123 }
124
125 #[test]
126 fn test_display_zero() {
127 let zero = i8::zero();
128
129 let candidate = Integer::<CurrentEnvironment, i8>::new(zero);
130 assert_eq!("0i8", &format!("{candidate}"));
131 }
132
133 #[test]
134 fn test_display_one() {
135 let one = i8::one();
136
137 let candidate = Integer::<CurrentEnvironment, i8>::new(one);
138 assert_eq!("1i8", &format!("{candidate}"));
139 }
140
141 #[test]
142 fn test_display_two() {
143 let one = i8::one();
144 let two = one + one;
145
146 let candidate = Integer::<CurrentEnvironment, i8>::new(two);
147 assert_eq!("2i8", &format!("{candidate}"));
148 }
149}