aoc

My solutions for the Advent of Code
git clone https://git.tronto.net/aoc
Download | Log | Files | Refs | README

common.rs (1250B)


      1 use std::collections::HashSet;
      2 
      3 fn get_dir(c: char) -> (i64, i64) {
      4     match c {
      5         'R' => (1, 0),
      6         'L' => (-1, 0),
      7         'U' => (0, 1),
      8         'D' => (0, -1),
      9         _ => panic!("Unexpected char")
     10     }
     11 }
     12 
     13 fn follow(lead: (i64, i64), trail: (i64, i64)) -> (i64, i64) {
     14     let max1 = |x: i64| x / (2 - (x%2).abs());
     15     let d = (max1(lead.0 - trail.0), max1(lead.1 - trail.1));
     16     (trail.0 + d.0, trail.1 + d.1)
     17 }
     18 
     19 fn step(r: &mut Vec<(i64, i64)>, d: (i64, i64)) {
     20     r[0] = (r[0].0 + d.0, r[0].1 + d.1);
     21     for i in 1..r.len() {
     22         if (r[i].0 - r[i-1].0).abs() > 1 || (r[i].1 - r[i-1].1).abs() > 1 {
     23             r[i] = follow(r[i-1], r[i]);
     24         } else {
     25             break;
     26         }
     27     }
     28 }
     29 
     30 pub fn simulate(n: usize) -> HashSet<(i64, i64)> {
     31     let mut r = vec![(0, 0); n];
     32     let mut visited = HashSet::<(i64, i64)>::new();
     33     visited.insert(r[n-1]);
     34 
     35     let mut line = String::new();
     36     while std::io::stdin().read_line(&mut line).unwrap() > 0 {
     37         let dir = get_dir(line.chars().nth(0).unwrap());
     38         let l = line[2..line.len()-1].parse::<usize>().unwrap();
     39         for _ in 0..l {
     40             step(&mut r, dir);
     41             visited.insert(r[n-1]);
     42         }
     43         line.clear();
     44     }
     45     visited
     46 }