Skip to content

Commit d080166

Browse files
authored
Merge pull request #2 from Starfunk/Update-0.2.0
Update 0.2.0
2 parents 8fed89c + aa2268e commit d080166

8 files changed

+934
-231
lines changed

Cargo.lock

+1-1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
[package]
22
name = "largeint"
3-
version = "0.1.0"
3+
version = "0.2.0"
44
authors = ["Maximilian Kahn <[email protected]>"]
55
license = "MIT"
6-
description = "A library that supports large integer arithmetic using LargeInt."
6+
description = "A library that supports large integer arithmetic."
77
readme = "README.md"
88
documentation = "https://docs.rs/largeint"
99
repository = "https://github.com/Starfunk/largeint"
10-
keywords = ["largeint", "large", "int","bigint","num"]
11-
categories = ["no-std"]
10+
keywords = ["largeint", "int", "large","integer"]
11+
categories = ["no-std", "data-structures"]
1212

1313
[dependencies]

README.md

+36-13
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
# largeint
2-
A library that implements the `LargeInt` type, used for working with arbitrarily large integers in Rust!
2+
A library that supports large integer arithmetic.
33

44
## Getting Started
55
First, add largeint to your dependencies:
66
```toml
77
[dependencies]
8-
largeint = "0.1.0"
8+
largeint = "0.2.0"
99
```
1010
Next, add this to the root of your crate to bring the contents of largeint into the scope of your project:
1111
```rust
@@ -14,18 +14,24 @@ extern crate largeint;
1414
use largeint::largeint::*;
1515
```
1616

17-
1817
You can then easily create many instances of `LargeInt`:
1918
```rust
2019
let largeint1 = new(String::from("999999999999999999999"), Sign::Positive);
2120
let largeint2 = new(String::from("999999999999999999999"), Sign::Negative);
2221
let largeint3 = new(String::from("0"), Sign::Unsigned);
2322
```
24-
An instance of `LargeInt` contains two fields, the scalar value of the integer stored as a `String` and the sign of the integer stored as the enum, `Sign`, which can be `Positive`, `Negative`, or `Unsigned` (note that `0` is the only integer that should be assigned `Unsigned`).
23+
An instance of `LargeInt` contains two fields, the scalar value of the integer stored as a `String` and the sign of the integer stored as the enum, `Sign`, which can be `Positive`, `Negative`, or `Unsigned` (note that `0` is the only integer that should be assigned `Unsigned`).
24+
25+
Using `new` to create an instance of `LargeInt` is highly recommended as there are checks in place to ensure that the the instance of `LargeInt` will be created properly. For example, creating an instance of a `LargeInt` with a scalar value of `0` using `new` will automatically assign `Sign::Unsigned` to the sign of the LargeInt even if you enter another `Sign` variant.
2526

26-
Using `new()` to create an instance of `LargeInt` is highly recommmended as there are checks in place to ensure that the `LargeInt` will be created properly.
27+
The purpose of this library is to provide an easy-to-use large integer implementation in Rust.
28+
The ideal user is one that is looking to write small scale projects for personal use and does
29+
not want to spend time a lot of time learning a complex crate such as num-bigint. For example,
30+
this library would be ideal for one looking to solve [Project Euler Problem 13](https://projecteuler.net/problem=13).
31+
However, the largeint library is not particularly efficient and therefore it is recommended to use
32+
a crate like num-bigint for more serious projects.
2733

28-
Refer to the documentation for more details.
34+
Let's see just how easy it is to start performing large integer arithmetic!
2935

3036
## An Example
3137

@@ -46,21 +52,38 @@ fn main() {
4652
// Subtracting two LargeInts.
4753
let largeint1 = new(String::from("33901489213409093401849249010492000112"), Sign::Negative);
4854
let largeint2 = new(String::from("100320394280329423048093284093240234809833999"), Sign::Negative);
49-
let largeint3 = largeint1.subtract(&largeint2);
55+
let largeint3 = largeint1.sub(&largeint2);
5056
let largeint4 = new(String::from("100320360378840209638999882243991224317833887"), Sign::Positive);
5157
assert_eq!(largeint3,largeint4);
52-
58+
59+
// Multiplying two LargeInts.
60+
let largeint1 = new(String::from("239014892134090934018492404920112"), Sign::Negative);
61+
let largeint2 = new(String::from("820948948039443908494308943885"), Sign::Negative);
62+
let largeint3 = largeint1.mul(&largeint2);
63+
let largeint4 = new(String::from("196219024263243108752932957733805138559777844813650340515915120"), Sign::Positive);
64+
assert_eq!(largeint3,largeint4);
65+
66+
// Dividing two LargeInts.
67+
let largeint1 = new(String::from("33901489213409093401849249010492088384894374938712"), Sign::Positive);
68+
let largeint2 = new(String::from("1003203942803294230480932840934343489333999"), Sign::Negative);
69+
let largeint3 = largeint1.div(&largeint2);
70+
let largeint4 = new(String::from("33793217"), Sign::Negative);
71+
assert_eq!(largeint3,largeint4);
72+
5373
//The get_int() method returns the scalar value of the LargeInt as a String.
5474
println!("The value of largeint1 is: {}", largeint1.get_int());
55-
75+
5676
//The get_sign() method returns the Sign of the LargeInt as a String.
57-
println!("The Sign of largeint1 is: {}", largeint1.get_sign());
77+
println!("The Sign of largeint1 is: {}", largeint1.get_sign());
5878
}
5979

6080
```
81+
## Updates
82+
Code Breaking Changes:
83+
The subtraction method has been renamed `sub` from `subtraction`.
84+
85+
New Library Additions:
86+
Multiplication, floor division - and remainder - have been added.
6187

6288
## License
6389
This project is licensed under the MIT License - see [LICENSE.md](https://github.com/Starfunk/largeint/blob/master/LICENSE) for more details.
64-
65-
## Future Updates
66-
Integer multiplication and division for `LargeInt` is currently being developed and should be released sometime in the next few weeks in the `"0.2.0"` update.

src/addition.rs

+51-1
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ pub fn addition(large1: &str, large2: &str) -> String {
99
let mut sum = vec![];
1010
let mut counter: u8 = 0;
1111
let mut input: u8;
12-
12+
1313
if large1.len() >= large2.len() {
1414
large3 = &large1;
1515
large4 = &large2;
@@ -52,3 +52,53 @@ pub fn addition(large1: &str, large2: &str) -> String {
5252
let digits = vec_to_str(&sum);
5353
digits
5454
}
55+
56+
57+
pub fn addition_2(large1: Vec<u8>, large2: Vec<u8>) -> Vec<u8> {
58+
let large3: &Vec<u8>;
59+
let large4: &Vec<u8>;
60+
let mut sum = vec![];
61+
let mut counter: u8 = 0;
62+
let mut input: u8;
63+
64+
if large1.len() >= large2.len() {
65+
large3 = &large1;
66+
large4 = &large2;
67+
} else {
68+
large3 = &large2;
69+
large4 = &large1;
70+
}
71+
let len_1 = large3.len();
72+
let len_2 = large4.len();
73+
for i in 0..len_2 {
74+
input = large3[len_1 - i - 1] + large4[len_2 - i - 1] + counter;
75+
if input >= 10 {
76+
input = input - 10;
77+
sum.insert(0, input);
78+
counter = 1;
79+
} else {
80+
sum.insert(0, input);
81+
counter = 0;
82+
}
83+
}
84+
if len_1 > len_2 {
85+
for i in (0..len_1 - len_2).rev() {
86+
input = large3[i] + counter;
87+
88+
if input == 10 {
89+
sum.insert(0, 0);
90+
counter = 1;
91+
} else {
92+
sum.insert(0, input);
93+
counter = 0;
94+
}
95+
}
96+
if counter == 1 {
97+
sum.insert(0, 1)
98+
}
99+
}
100+
if len_1 == len_2 && counter == 1 {
101+
sum.insert(0, 1);
102+
}
103+
sum
104+
}

src/division.rs

+155
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,155 @@
1+
use largeint::*;
2+
use multiplication::multiplication_1;
3+
4+
pub fn division(large1: &str, large2: &str) -> Vec<String> {
5+
let mut divided = String::from("");
6+
let mut remainder_largeint: LargeInt;
7+
let mut remainder_str = String::from("");
8+
let output_vec: Vec<String>;
9+
let sign = Sign::Positive;
10+
let large2 = new(String::from(large2), sign);
11+
let large1_length = large1.len();
12+
let mut large1_slice: &str;
13+
let mut flag = true;
14+
let mut counter = 0;
15+
while flag == true {
16+
for i in 1..large1_length + 1 {
17+
large1_slice = &large1[0..i];
18+
let large1_piece = new(String::from(large1_slice), sign);
19+
if large1_piece.compare(&large2) == Compare::Smaller {
20+
counter += 1;
21+
continue
22+
} else if large1_piece.compare(&large2) == Compare::Larger {
23+
for i in 1..10 {
24+
let index = i.to_string();
25+
let index_str= to_vec(&index[..]);
26+
let large2_vec = to_vec(&large2.digits);
27+
let product = multiplication_1(&large2_vec, &index_str);
28+
let product_vec = vec_to_str(&product);
29+
let product_largeint = new(product_vec, sign);
30+
if large1_piece.compare(&product_largeint) == Compare::Smaller {
31+
let index1 = i - 1;
32+
let index1_str = index1.to_string();
33+
divided.push_str(&index1.to_string());
34+
let index1_largeint = to_vec(&index1_str);
35+
let product_2 = multiplication_1(&large2_vec, &index1_largeint);
36+
let product_vec_2 = vec_to_str(&product_2);
37+
let product_largeint_2 = new(product_vec_2, sign);
38+
remainder_largeint = large1_piece.sub(&product_largeint_2);
39+
remainder_str = remainder_largeint.digits;
40+
flag = false;
41+
break
42+
} else if large1_piece.compare(&product_largeint) == Compare::Equal {
43+
remainder_str = String::from("0");
44+
divided.push_str(&index);
45+
flag = false;
46+
break
47+
}
48+
}
49+
counter += 1;
50+
} else if large1_piece.compare(&large2) == Compare::Equal {
51+
remainder_str.push_str("0");
52+
divided.push_str("1");
53+
counter += 1;
54+
flag = false;
55+
}
56+
break
57+
}
58+
}
59+
if counter != large1_length {
60+
for _ in counter..large1_length + 1 {
61+
if counter == large1_length {
62+
break
63+
}
64+
if remainder_str == String::from("0") && &large1[counter..counter+1] == "0" {
65+
remainder_str = String::from("0");
66+
divided.push_str("0");
67+
counter += 1;
68+
}
69+
else if remainder_str == String::from("0") && &large1[counter..counter+1] != "0" {
70+
remainder_str = large1[counter..counter+1].to_string();
71+
let remainder_largeint = new(remainder_str.clone(), sign);
72+
if remainder_largeint.compare(&large2) == Compare::Smaller {
73+
divided.push_str("0");
74+
} else if remainder_largeint.compare(&large2) == Compare::Larger {
75+
let output_tuple = find_the_highest_divider(&remainder_str, &large2, &mut divided);
76+
divided = output_tuple.0;
77+
remainder_str = output_tuple.1;
78+
} else {
79+
remainder_str = String::from("0");
80+
divided.push_str("0");
81+
}
82+
counter += 1;
83+
} else {
84+
remainder_str.push_str(&large1[counter..counter+1]);
85+
let mut remainder_largeint = new(remainder_str.clone(), sign);
86+
if remainder_largeint.compare(&large2) == Compare::Smaller {
87+
divided.push_str("0");
88+
} else if remainder_largeint.compare(&large2) == Compare::Larger {
89+
let output_tuple = find_the_highest_divider(&remainder_str, &large2, &mut divided);
90+
divided = output_tuple.0;
91+
remainder_str = output_tuple.1;
92+
} else {
93+
remainder_str = String::from("0");
94+
divided.push_str("1");
95+
}
96+
counter += 1;
97+
}
98+
}
99+
}
100+
output_vec = vec![divided, remainder_str];
101+
output_vec
102+
}
103+
104+
fn find_the_highest_divider(remainder: &String, large2: &LargeInt, divided: &mut String) -> (String, String) {
105+
let mut remainder_str = String::from("0");
106+
let sign = Sign::Positive;
107+
let remainder_largeint = new(remainder.clone(), sign);
108+
let large2_vec = to_vec(&large2.digits);
109+
let remainder2_largeint: LargeInt;
110+
let mut index: String;
111+
let mut index_vec: Vec<u8>;
112+
let mut product: Vec<u8>;
113+
for i in 0..10 {
114+
index = i.to_string();
115+
index_vec = to_vec(&index[..]);
116+
if i == 0 {
117+
product = vec![0]
118+
} else {
119+
product = multiplication_1(&large2_vec, &index_vec);
120+
}
121+
let product_str = vec_to_str(&product);
122+
let product_largeint = new(product_str, sign);
123+
if remainder_largeint.compare(&product_largeint) == Compare::Smaller {
124+
let index1 = i - 1;
125+
let index1_vec: Vec<u8>;
126+
let index1_str: String;
127+
if index1 == 0 {
128+
index1_str = String::from("0");
129+
} else {
130+
index1_str = index1.to_string();
131+
}
132+
index1_vec = to_vec(&index1_str[..]);
133+
let product1 = multiplication_1(&large2_vec, &index1_vec);
134+
let product1_str = vec_to_str(&product1 );
135+
let product1_largeint = new(product1_str, sign);
136+
divided.push_str(&index1.to_string());
137+
remainder2_largeint = remainder_largeint.sub(&product1_largeint);
138+
remainder_str = remainder2_largeint.digits;
139+
break
140+
} else if i == 9 {
141+
divided.push_str(&index.to_string());
142+
remainder2_largeint = remainder_largeint.sub(&product_largeint);
143+
remainder_str = remainder2_largeint.digits;
144+
break
145+
}
146+
else if remainder_largeint.compare(&product_largeint) == Compare::Equal {
147+
divided.push_str(&index);
148+
remainder_str = String::from("0");
149+
break
150+
} else {
151+
remainder_str = String::from("0");
152+
}
153+
}
154+
(divided.clone(), remainder_str)
155+
}

0 commit comments

Comments
 (0)