Skip to content

Commit b4b5071

Browse files
authored
Rust implementation of the jarvis march algorithm (#723)
1 parent 77dfff6 commit b4b5071

File tree

3 files changed

+67
-0
lines changed

3 files changed

+67
-0
lines changed

CONTRIBUTORS.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,3 +52,4 @@ This file lists everyone, who contributed to this repo and wanted to show up her
5252
- Jonathan D B Van Schenck
5353
- James Goytia
5454
- Amaras
55+
- Jonathan Dönszelmann
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
2+
type Point = (i64, i64);
3+
4+
// Is the turn counter clockwise?
5+
fn turn_counter_clockwise(p1: Point, p2: Point, p3: Point) -> bool {
6+
(p3.1 - p1.1) * (p2.0 - p1.0) >= (p2.1 - p1.1) * (p3.0 - p1.0)
7+
}
8+
9+
fn jarvis_march(gift: &[Point]) -> Option<Vec<Point>> {
10+
// There can only be a convex hull if there are more than 2 points
11+
if gift.len() < 3 {
12+
return None;
13+
}
14+
15+
let leftmost_point = gift
16+
// Iterate over all points
17+
.iter()
18+
// Find the point with minimum x
19+
.min_by_key(|i| i.0)
20+
// If there are no points in the gift, there might
21+
// not be a minimum. Unwrap fails (panics) the program
22+
// if there wasn't a minimum, but we know there always
23+
// is because we checked the size of the gift.
24+
.unwrap()
25+
.clone();
26+
27+
let mut hull = vec![leftmost_point];
28+
29+
let mut point_on_hull = leftmost_point;
30+
loop {
31+
// Search for the next point on the hull
32+
let mut endpoint = gift[0];
33+
for i in 1..gift.len() {
34+
if endpoint == point_on_hull || !turn_counter_clockwise(gift[i], hull[hull.len() - 1], endpoint) {
35+
endpoint = gift[i];
36+
}
37+
}
38+
39+
point_on_hull = endpoint;
40+
41+
// Stop whenever we got back to the same point
42+
// as we started with, and we wrapped the gift
43+
// completely.
44+
if hull[0] == endpoint {
45+
break;
46+
} else {
47+
hull.push(point_on_hull);
48+
}
49+
}
50+
51+
Some(hull)
52+
}
53+
54+
fn main() {
55+
let test_gift = vec![
56+
(-5, 2), (5, 7), (-6, -12), (-14, -14), (9, 9),
57+
(-1, -1), (-10, 11), (-6, 15), (-6, -8), (15, -9),
58+
(7, -7), (-2, -9), (6, -5), (0, 14), (2, 8)
59+
];
60+
61+
let hull = jarvis_march(&test_gift);
62+
63+
println!("The points in the hull are: {:?}", hull);
64+
}

contents/jarvis_march/jarvis_march.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,8 @@ Since this algorithm, there have been many other algorithms that have advanced t
4848
[import, lang:"go"](code/golang/jarvis.go)
4949
{% sample lang="v" %}
5050
[import, lang:"v"](code/v/jarvis.v)
51+
{% sample lang="rust" %}
52+
[import, lang:"rust"](code/rust/jarvis_march.rs)
5153
{% endmethod %}
5254

5355
<script>

0 commit comments

Comments
 (0)