From b321a1a5c0ab924bd6ff3786b4b5f50e3738cbea Mon Sep 17 00:00:00 2001 From: "T. Jameson Little" Date: Thu, 29 May 2014 18:39:33 -0600 Subject: [PATCH] add factor --- Makefile | 1 + README.md | 1 - factor/factor.rs | 105 +++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 106 insertions(+), 1 deletion(-) create mode 100644 factor/factor.rs diff --git a/Makefile b/Makefile index 26e6ccf32..72364b595 100644 --- a/Makefile +++ b/Makefile @@ -14,6 +14,7 @@ PROGS := \ echo \ env \ du \ + factor \ false \ fold \ md5sum \ diff --git a/README.md b/README.md index 95872fe98..f57754021 100644 --- a/README.md +++ b/README.md @@ -86,7 +86,6 @@ To do - expand (in progress) - expr - extent-scan -- factor - find-mount-point - fmt - getlimits diff --git a/factor/factor.rs b/factor/factor.rs new file mode 100644 index 000000000..5d78cab0e --- /dev/null +++ b/factor/factor.rs @@ -0,0 +1,105 @@ +#![crate_id(name="factor", vers="1.0.0", author="T. Jameson Little")] +#![feature(macro_rules)] + +/* +* This file is part of the uutils coreutils package. +* +* (c) T. Jameson Little +* +* For the full copyright and license information, please view the LICENSE file +* that was distributed with this source code. +*/ + +extern crate getopts; +extern crate libc; + +use std::u64; +use std::os; +use std::vec::{Vec}; +use std::io::{stdin}; + +#[path="../common/util.rs"] +mod util; + +static VERSION: &'static str = "1.0.0"; +static NAME: &'static str = "factor"; + +fn factor(mut num: u64) -> Vec { + let mut ret = Vec::new(); + + while num % 2 == 0 { + num /= 2; + ret.push(2); + } + let mut i = 3; + while i * i <= num { + while num % i == 0 { + num /= i; + ret.push(i); + } + i += 2; + } + if num > 1 { + ret.push(num); + } + ret +} + +fn print_factors(num: u64) { + print!("{}:", num); + for fac in factor(num).iter() { + print!(" {}", fac); + } + println!(""); +} + +fn print_factors_str(num_str: &str) { + let num = match u64::parse_bytes(num_str.as_bytes(), 10) { + Some(x) => x, + None => { crash!(1, "{} not a number", num_str); } + }; + print_factors(num); +} + + +#[allow(dead_code)] +fn main() { uumain(os::args()); } + +pub fn uumain(args: Vec) { + let program = args.get(0).as_slice(); + let opts = [ + getopts::optflag("h", "help", "show this help message"), + getopts::optflag("v", "version", "print the version and exit"), + ]; + + let matches = match getopts::getopts(args.tail(), opts) { + Ok(m) => m, + Err(f) => crash!(1, "Invalid options\n{}", f.to_err_msg()) + }; + + if matches.opt_present("help") { + print!("{program} {version}\n\ + \n\ + Usage:\n\ + \t{program} [NUMBER]...\n\ + \t{program} [OPTION]\n\ + \n\ + {usage}", program = program, version = VERSION, usage = getopts::usage("Print the prime factors of the given number(s). \ + If none are specified, read from standard input.", opts)); + return; + } + if matches.opt_present("version") { + println!("{} {}", program, VERSION); + return; + } + + if matches.free.is_empty() { + for line in stdin().lines() { + print_factors_str(line.unwrap().as_slice().trim()); + } + } else { + for num_str in matches.free.iter() { + print_factors_str(num_str.as_slice()); + } + } +}