Skip to content

Commit 9c1be05

Browse files
authored
Add Zeckendorf in Rust (#5342)
1 parent b711de2 commit 9c1be05

1 file changed

Lines changed: 69 additions & 0 deletions

File tree

archive/r/rust/zeckendorf.rs

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
use std::cmp::PartialOrd;
2+
use std::env::args;
3+
use std::ops::{Add, SubAssign};
4+
use std::process::exit;
5+
use std::str::FromStr;
6+
7+
fn usage() -> ! {
8+
println!("Usage: please input a non-negative integer");
9+
exit(0);
10+
}
11+
12+
fn parse_int<T: FromStr>(s: &str) -> Result<T, <T as FromStr>::Err> {
13+
s.trim().parse::<T>()
14+
}
15+
16+
fn get_fibonacci_values<T>(value: T) -> Vec<T>
17+
where
18+
T: Add<Output = T> + PartialOrd + From<u8> + Copy
19+
{
20+
let mut fibs = vec![];
21+
let mut a: T = T::from(1);
22+
let mut b: T = T::from(2);
23+
while a <= value {
24+
fibs.push(a);
25+
(a, b) = (b, a + b);
26+
}
27+
28+
fibs
29+
}
30+
31+
fn get_zeckendorf_values<T>(value: T) -> Vec<T>
32+
where
33+
T: Add<Output = T> + SubAssign + PartialOrd + From<u8> + Copy
34+
{
35+
let fibs = get_fibonacci_values(value);
36+
let mut zecks = vec![];
37+
let mut n = (fibs.len() as i32) - 1;
38+
let mut remaining = value;
39+
while n >= 0 && remaining > T::from(0) {
40+
let f = fibs[n as usize];
41+
if remaining >= f {
42+
zecks.push(f);
43+
remaining -= f;
44+
n -= 2;
45+
} else {
46+
n -= 1;
47+
}
48+
}
49+
50+
zecks
51+
}
52+
53+
fn main() {
54+
let mut args = args().skip(1);
55+
56+
// Exit if 1st command-line argument not an integer
57+
let input_num: i32 = args
58+
.next()
59+
.and_then(|s| parse_int(&s).ok())
60+
.unwrap_or_else(|| usage());
61+
62+
// Exit if value is negative
63+
if input_num < 0 {
64+
usage();
65+
}
66+
67+
let zecks = get_zeckendorf_values::<i32>(input_num);
68+
println!("{:?}", zecks);
69+
}

0 commit comments

Comments
 (0)