pub fn find_saddle_points(input: &[Vec<u64>]) -> Vec<(usize, usize)> {
    let mut row_max = vec![Vec::new(); input.len()];
    let mut col_min: Vec<Vec<(usize, u64)>> = vec![Vec::new(); input[0].len()];

    for (row, values) in input.iter().enumerate() {
        for (col, &value) in values.iter().enumerate() {
            let mut c = &mut col_min[col];

            if c.is_empty() || c[0].1 == value {
                c.push((row, value));
            } else if c[0].1 > value {
                c.clear();
                c.push((row, value));
            }

            let mut r = &mut row_max[row];

            if r.is_empty() || r[0] == value {
                r.push(value);
            } else if r[0] < value {
                r.clear();
                r.push(value);
            }
        }
    }

    col_min
        .iter()
        .enumerate()
        .fold(Vec::new(), |mut points, (col, values)| {
            let mut col_points = values
                .iter()
                .filter(|c| row_max[c.0].contains(&c.1))
                .map(|c| (c.0, col))
                .collect();

            points.append(&mut col_points);
            points
        })
}

fn is_saddle_point(input: &[Vec<u64>], px: usize, py: usize) -> bool {
    let value = input[py][px];

    for y in 0..input.len() {
        if input[y][px] < value {
            return false;
        }
    }

    for x in 0..input[0].len() {
        if input[py][x] > value {
            return false;
        }
    }

    true
}

pub fn find_saddle_points(input: &[Vec<u64>]) -> Vec<(usize, usize)> {
    let mut saddle_points = Vec::new();

    for y in 0..input.len() {
        for x in 0..input[y].len() {
            if is_saddle_point(input, x, y) {
                saddle_points.push((y, x));
            }
        }
    }

    saddle_points
}

--- 
+++ 
@@ -1,31 +1,40 @@
-fn is_saddle_point(input: &[Vec<u64>], px: usize, py: usize) -> bool {
-    let value = input[py][px];
+pub fn find_saddle_points(input: &[Vec<u64>]) -> Vec<(usize, usize)> {
+    let mut row_max = vec![Vec::new(); input.len()];
+    let mut col_min: Vec<Vec<(usize, u64)>> = vec![Vec::new(); input[0].len()];
 
-    for y in 0..input.len() {
-        if input[y][px] < value {
-            return false;
-        }
-    }
+    for (row, values) in input.iter().enumerate() {
+        for (col, &value) in values.iter().enumerate() {
+            let mut c = &mut col_min[col];
 
-    for x in 0..input[0].len() {
-        if input[py][x] > value {
-            return false;
-        }
-    }
+            if c.is_empty() || c[0].1 == value {
+                c.push((row, value));
+            } else if c[0].1 > value {
+                c.clear();
+                c.push((row, value));
+            }
 
-    true
-}
+            let mut r = &mut row_max[row];
 
-pub fn find_saddle_points(input: &[Vec<u64>]) -> Vec<(usize, usize)> {
-    let mut saddle_points = Vec::new();
-
-    for y in 0..input.len() {
-        for x in 0..input[y].len() {
-            if is_saddle_point(input, x, y) {
-                saddle_points.push((y, x));
+            if r.is_empty() || r[0] == value {
+                r.push(value);
+            } else if r[0] < value {
+                r.clear();
+                r.push(value);
             }
         }
     }
 
-    saddle_points
+    col_min
+        .iter()
+        .enumerate()
+        .fold(Vec::new(), |mut points, (col, values)| {
+            let mut col_points = values
+                .iter()
+                .filter(|c| row_max[c.0].contains(&c.1))
+                .map(|c| (c.0, col))
+                .collect();
+
+            points.append(&mut col_points);
+            points
+        })
 }
Improve solution for Saddle Points
