bigdecimal/arithmetic/
decimal.rs1#[allow(dead_code)]
10pub fn dec_shift_right_u32(x: u32, n: usize) -> u32 {
11    match n {
12        0 => x,
13        1 => x / 10,
14        2 => x / 100,
15        3 => x / 1000,
16        4 => x / 10_000,
17        5 => x / 100_000,
18        6 => x / 1000_000,
19        7 => x / 10_000_000,
20        8 => x / 100_000_000,
21        9 => x / 1000_000_000,
22        _ => 0,
23    }
24}
25
26
27#[allow(dead_code)]
29pub fn dec_shift_right_u64(x: u64, n: usize) -> u64 {
30    match n {
31        0 => x,
32        1 => x / 10,
33        2 => x / 100,
34        3 => x / 1000,
35        4 => x / 10_000,
36        5 => x / 100_000,
37        6 => x / 1000_000,
38        7 => x / 10_000_000,
39        8 => x / 100_000_000,
40        9 => x / 1000_000_000,
41        10 => x / 10_000_000_000,
42        11 => x / 100_000_000_000,
43        12 => x / 1000_000_000_000,
44        13 => x / 10_000_000_000_000,
45        14 => x / 100_000_000_000_000,
46        15 => x / 1000_000_000_000_000,
47        16 => x / 10_000_000_000_000_000,
48        17 => x / 100_000_000_000_000_000,
49        18 => x / 1000_000_000_000_000_000,
50        19 => x / 10_000_000_000_000_000_000,
51        _ => 0,
52    }
53}
54
55
56macro_rules! count_digits {
57    ($n:ident : u128) => {
58               if $n >= 100000000000000000000000000000000000000 {
59            39
60        } else if $n >= 10000000000000000000000000000000000000 {
61            38
62        } else if $n >= 1000000000000000000000000000000000000 {
63            37
64        } else if $n >= 100000000000000000000000000000000000 {
65            36
66        } else if $n >= 10000000000000000000000000000000000 {
67            35
68        } else if $n >= 1000000000000000000000000000000000 {
69            34
70        } else if $n >= 100000000000000000000000000000000 {
71            33
72        } else if $n >= 10000000000000000000000000000000 {
73            32
74        } else if $n >= 1000000000000000000000000000000 {
75            31
76        } else if $n >= 100000000000000000000000000000 {
77            30
78        } else if $n >= 10000000000000000000000000000 {
79            29
80        } else if $n >= 1000000000000000000000000000 {
81            28
82        } else if $n >= 100000000000000000000000000 {
83            27
84        } else if $n >= 10000000000000000000000000 {
85            26
86        } else if $n >= 1000000000000000000000000 {
87            25
88        } else if $n >= 100000000000000000000000 {
89            24
90        } else if $n >= 10000000000000000000000 {
91            23
92        } else if $n >= 1000000000000000000000 {
93            22
94        } else if $n >= 100000000000000000000 {
95            21
96        } else {
97            count_digits!($n:u64)
98        }
99    };
100    ($n:ident : u64) => {
101               if $n >= 10000000000000000000 {
102            20
103        } else if $n >= 1000000000000000000 {
104            19
105        } else if $n >= 100000000000000000 {
106            18
107        } else if $n >= 10000000000000000 {
108            17
109        } else if $n >= 1000000000000000 {
110            16
111        } else if $n >= 100000000000000 {
112            15
113        } else if $n >= 10000000000000 {
114            14
115        } else if $n >= 1000000000000 {
116            13
117        } else if $n >= 100000000000 {
118            12
119        } else if $n >= 10000000000 {
120            11
121        } else if $n >= 1000000000 {
122            10
123        } else {
124            count_digits!($n:u32)
125        }
126    };
127    ($n:ident : u32) => {
128               if $n >= 1000000000 {
129            10
130        } else if $n >= 100000000 {
131            9
132        } else if $n >= 10000000 {
133            8
134        } else if $n >= 1000000 {
135            7
136        } else if $n >= 100000 {
137            6
138        } else {
139            count_digits!($n:u16)
140        }
141    };
142    ($n:ident : u16) => {
143               if $n >= 100000 {
144            6
145        } else if $n >= 10000 {
146            5
147        } else if $n >= 1000 {
148            4
149        } else {
150            count_digits!($n:u8)
151        }
152    };
153    ($n:ident : u8) => {
154               if $n >= 100 {
155            3
156        } else if $n >= 10 {
157            2
158        } else {
159            1
160        }
161    };
162}
163
164pub(crate) fn count_digits_u32(n: u32) -> usize {
166    if n >= 1000000000 {
    10
} else if n >= 100000000 {
    9
} else if n >= 10000000 {
    8
} else if n >= 1000000 {
    7
} else if n >= 100000 {
    6
} else {
    if n >= 100000 {
        6
    } else if n >= 10000 {
        5
    } else if n >= 1000 {
        4
    } else { if n >= 100 { 3 } else if n >= 10 { 2 } else { 1 } }
}count_digits!(n:u32)
167
168}
169
170pub(crate) fn count_digits_u64(n: u64) -> usize {
172    if (n >> 32) == 0 {
173       count_digits_u32(n as u32)
174    } else {
175       if n >= 10000000000000000000 {
    20
} else if n >= 1000000000000000000 {
    19
} else if n >= 100000000000000000 {
    18
} else if n >= 10000000000000000 {
    17
} else if n >= 1000000000000000 {
    16
} else if n >= 100000000000000 {
    15
} else if n >= 10000000000000 {
    14
} else if n >= 1000000000000 {
    13
} else if n >= 100000000000 {
    12
} else if n >= 10000000000 {
    11
} else if n >= 1000000000 {
    10
} else {
    if n >= 1000000000 {
        10
    } else if n >= 100000000 {
        9
    } else if n >= 10000000 {
        8
    } else if n >= 1000000 {
        7
    } else if n >= 100000 {
        6
    } else {
        if n >= 100000 {
            6
        } else if n >= 10000 {
            5
        } else if n >= 1000 {
            4
        } else { if n >= 100 { 3 } else if n >= 10 { 2 } else { 1 } }
    }
}count_digits!(n:u64)
176    }
177}
178
179pub(crate) fn count_digits_u128(n: u128) -> usize {
181    if (n >> 64) == 0 {
182       count_digits_u64(n as u64)
183    } else {
184       if n >= 100000000000000000000000000000000000000 {
    39
} else if n >= 10000000000000000000000000000000000000 {
    38
} else if n >= 1000000000000000000000000000000000000 {
    37
} else if n >= 100000000000000000000000000000000000 {
    36
} else if n >= 10000000000000000000000000000000000 {
    35
} else if n >= 1000000000000000000000000000000000 {
    34
} else if n >= 100000000000000000000000000000000 {
    33
} else if n >= 10000000000000000000000000000000 {
    32
} else if n >= 1000000000000000000000000000000 {
    31
} else if n >= 100000000000000000000000000000 {
    30
} else if n >= 10000000000000000000000000000 {
    29
} else if n >= 1000000000000000000000000000 {
    28
} else if n >= 100000000000000000000000000 {
    27
} else if n >= 10000000000000000000000000 {
    26
} else if n >= 1000000000000000000000000 {
    25
} else if n >= 100000000000000000000000 {
    24
} else if n >= 10000000000000000000000 {
    23
} else if n >= 1000000000000000000000 {
    22
} else if n >= 100000000000000000000 {
    21
} else {
    if n >= 10000000000000000000 {
        20
    } else if n >= 1000000000000000000 {
        19
    } else if n >= 100000000000000000 {
        18
    } else if n >= 10000000000000000 {
        17
    } else if n >= 1000000000000000 {
        16
    } else if n >= 100000000000000 {
        15
    } else if n >= 10000000000000 {
        14
    } else if n >= 1000000000000 {
        13
    } else if n >= 100000000000 {
        12
    } else if n >= 10000000000 {
        11
    } else if n >= 1000000000 {
        10
    } else {
        if n >= 1000000000 {
            10
        } else if n >= 100000000 {
            9
        } else if n >= 10000000 {
            8
        } else if n >= 1000000 {
            7
        } else if n >= 100000 {
            6
        } else {
            if n >= 100000 {
                6
            } else if n >= 10000 {
                5
            } else if n >= 1000 {
                4
            } else { if n >= 100 { 3 } else if n >= 10 { 2 } else { 1 } }
        }
    }
}count_digits!(n:u128)
185    }
186}
187
188pub(crate) fn count_digits_bigint(n: &num_bigint::BigInt) -> u64 {
190    count_digits_biguint(n.magnitude())
191}
192
193pub(crate) fn count_digits_biguint(n: &num_bigint::BigUint) -> u64 {
195    use num_traits::ToPrimitive;
196
197    if let Some(n) = n.to_u64() {
198        return count_digits_u64(n) as u64;
199    }
200
201    let mut digits = (n.bits() as f64 / super::LOG2_10) as u64;
202    let mut num = super::ten_to_the_uint(digits);
204    if true {
    if !(n * 10u8 >= num) {
        ::core::panicking::panic("assertion failed: n * 10u8 >= num")
    };
};debug_assert!(n * 10u8 >= num);
205
206    while n >= &num {
207        num *= 10u8;
208        digits += 1;
209    }
210    digits
211}
212
213pub(crate) fn get_power_of_ten_u64(n: u64) -> Option<u8> {
215    match n {
216        0 => Some(0),
217        10 => Some(1),
218        100 => Some(2),
219        1000 => Some(3),
220        10000 => Some(4),
221        100000 => Some(5),
222        1000000 => Some(6),
223        10000000 => Some(7),
224        100000000 => Some(8),
225        1000000000 => Some(9),
226        10000000000 => Some(10),
227        n => {
228            let (q, r) = num_integer::div_rem(n, 10000000000);
229            if r == 0 {
230                get_power_of_ten_u64(q).map(|p| p + 10)
231            } else {
232                None
233            }
234        }
235    }
236}
237
238#[cfg(test)]
239mod test {
240    use super::*;
241    include!("decimal.tests.rs");
242}