Skip to content

Instantly share code, notes, and snippets.

@kevinmartinjos
Created January 21, 2019 19:01
Show Gist options
  • Save kevinmartinjos/c8ca7949e06c85a04076ac7183f27cf9 to your computer and use it in GitHub Desktop.
Save kevinmartinjos/c8ca7949e06c85a04076ac7183f27cf9 to your computer and use it in GitHub Desktop.
PIM book polynomials - 1
extern crate rand;
use std::io;
use rand::Rng;
fn main() {
let mut secret_passcode_str = String::new();
println!("What's the secret passcode?");
io::stdin().read_line(&mut secret_passcode_str).expect("Failed to read line");
let secret_passcode = secret_passcode_str.trim().parse::<i32>().expect("Wanted a number");
println!("This is the secret: {}", secret_passcode);
println!("How many parts?");
let mut parts_str = String::new();
io::stdin().read_line(&mut parts_str).expect("Failed to read line");
let required_parts: i32 = parts_str.trim().parse().expect("not a number");
let required_degree = required_parts - 1;
let coeffs: Vec<i32> = create_polynomical_of_degree(required_degree, secret_passcode);
let parts: Vec<(i32, i32)> = create_parts(coeffs, required_parts);
print_parts(&parts);
println!("Time to put things to test. Please enter your secret codes");
let input_parts: Vec<i32> = ask_everyone_their_secret_codes(required_parts);
let secret_code: i32 = decipher_secret_code(input_parts);
println!("The deciphered secret code is: {}", secret_code);
}
fn decipher_secret_code(input_parts: Vec<i32>) -> i32 {
let mut polynomial_value: i32 = 0;
let n = input_parts.len();
for (i, yi) in input_parts.iter().enumerate() {
let xi = i as i32 + 1;
let mut product = 1.0;
for j in 1..n+1 {
let xj = j as i32;
if xj == xi {
continue;
}
product *= (-1 * xj) as f64/(xi - xj) as f64;
}
let term = yi * product as i32;
polynomial_value += term;
}
return polynomial_value;
}
fn ask_everyone_their_secret_codes(required_parts: i32) -> Vec<i32> {
let mut parts: Vec<i32> = Vec::new();
for _i in 0..required_parts {
let mut input_str = String::new();
io::stdin().read_line(&mut input_str).expect("Failed to read line");
let secret_code_part: i32 = input_str.trim().parse().expect("not a number");
parts.push(secret_code_part);
}
return parts;
}
fn print_parts(parts: &Vec<(i32, i32)>) {
println!("The parts are:");
for (i, code_part) in parts.iter() {
println!("({}, {})", i, code_part);
}
}
fn create_parts(coeffs: Vec<i32>, required_parts: i32) -> Vec<(i32, i32)> {
let mut parts: Vec<(i32, i32)> = Vec::new();
for _i in 1..required_parts+1 {
let value = value_of_polynomial_at(&coeffs, _i);
parts.push((_i, value));
}
return parts;
}
fn value_of_polynomial_at(coeffs: &Vec<i32>, value: i32) -> i32 {
let mut sum: i32 = 0;
for(i, coeff) in coeffs.iter().enumerate() {
sum += coeff * i32::pow(value, i as u32);
}
return sum;
}
fn create_polynomical_of_degree(required_degree: i32, secret_passcode: i32) -> Vec<i32> {
let mut coeffs : Vec<i32> = Vec::new();
let zero_coeff: i32 = secret_passcode;
coeffs.push(zero_coeff);
for _i in 1..required_degree+1 {
let coeff = rand::thread_rng().gen_range(0, 100);
coeffs.push(coeff)
}
return coeffs;
}
fn print_polynomial(coeffs: &Vec<i32>) {
for (i, coeff) in coeffs.iter().enumerate() {
print!("{}x^{} + ", coeff, i);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment