试除法

  1. fn floor(value: f64, scale: u8) -> f64 {
  2. let multiplier = 10i64.pow(scale as u32) as f64;
  3. (value * multiplier).floor()
  4. }
  5. fn double_to_int(amount: f64) -> i128 {
  6. amount.round() as i128
  7. }
  8. pub fn trial_division(mut num: i128) -> Vec<i128> {
  9. let mut result: Vec<i128> = vec![];
  10. while num % 2 == 0 {
  11. result.push(2);
  12. num /= 2;
  13. num = double_to_int(floor(num as f64, 0))
  14. }
  15. let mut f: i128 = 3;
  16. while f.pow(2) <= num {
  17. if num % f == 0 {
  18. result.push(f);
  19. num /= f;
  20. num = double_to_int(floor(num as f64, 0))
  21. } else {
  22. f += 2
  23. }
  24. }
  25. if num != 1 {
  26. result.push(num)
  27. }
  28. result
  29. }
  30. #[cfg(test)]
  31. mod tests {
  32. use super::*;
  33. #[test]
  34. fn basic() {
  35. assert_eq!(trial_division(9), vec!(3, 3));
  36. assert_eq!(trial_division(10), vec!(2, 5));
  37. assert_eq!(trial_division(11), vec!(11));
  38. assert_eq!(trial_division(33), vec!(3, 11));
  39. assert_eq!(trial_division(2003), vec!(2003));
  40. assert_eq!(trial_division(100001), vec!(11, 9091));
  41. }
  42. }