[2018][rust] clippy
change nvylooyzozylkkvwpumsxmyyrsxkppyp
commit 2b7f7868a184060f1b90763b7e5ddf03dd2325d3
author Alpha Chen <alpha.chen@gmail.com>
date
parent umvnmmrv
diff --git a/2018/rust/src/bin/day_15.rs b/2018/rust/src/bin/day_15.rs
index 035020c..4d64577 100644
--- a/2018/rust/src/bin/day_15.rs
+++ b/2018/rust/src/bin/day_15.rs
@@ -8,7 +8,7 @@ use advent_of_code::main;
 
 main!();
 
-fn solve(input: &str) -> Result<String, Box<Error>> {
+fn solve(_input: &str) -> Result<String, Box<Error>> {
     unimplemented!();
 }
 
@@ -458,7 +458,7 @@ enum Race {
 }
 
 impl Race {
-    fn enemy(&self) -> Race {
+    fn enemy(self) -> Race {
         match self {
             Race::Elf => Race::Goblin,
             Race::Goblin => Race::Elf,
diff --git a/2018/rust/src/bin/day_19.rs b/2018/rust/src/bin/day_19.rs
new file mode 100644
index 0000000..8e9054d
--- /dev/null
+++ b/2018/rust/src/bin/day_19.rs
@@ -0,0 +1,201 @@
+use std::error::Error;
+use std::str::FromStr;
+
+use regex::Regex;
+
+use advent_of_code::main;
+
+main!();
+
+fn solve(input: &str) -> Result<String, Box<Error>> {
+    let mut program: Program = input.parse()?;
+    program.registers[0] = 1;
+    let registers = program.last().unwrap();
+    let output = registers[0].to_string();
+    Ok(output)
+}
+
+type Registers = [usize; 6];
+
+struct Program {
+    ip: usize,
+    instructions: Vec<Instruction>,
+    registers: Registers,
+}
+
+impl Program {
+    fn execute(&mut self, i: &Instruction) {
+        match i.opcode {
+            Opcode::Addr => self.registers[i.c] = self.registers[i.a] + self.registers[i.b],
+            Opcode::Addi => self.registers[i.c] = self.registers[i.a] + i.b,
+            Opcode::Mulr => self.registers[i.c] = self.registers[i.a] * self.registers[i.b],
+            Opcode::Muli => self.registers[i.c] = self.registers[i.a] * i.b,
+            Opcode::Banr => self.registers[i.c] = self.registers[i.a] & self.registers[i.b],
+            Opcode::Bani => self.registers[i.c] = self.registers[i.a] & i.b,
+            Opcode::Borr => self.registers[i.c] = self.registers[i.a] | self.registers[i.b],
+            Opcode::Bori => self.registers[i.c] = self.registers[i.a] | i.b,
+            Opcode::Setr => self.registers[i.c] = self.registers[i.a],
+            Opcode::Seti => self.registers[i.c] = i.a,
+            Opcode::Gtir => self.registers[i.c] = if i.a > self.registers[i.b] { 1 } else { 0 },
+            Opcode::Gtri => self.registers[i.c] = if self.registers[i.a] > i.b { 1 } else { 0 },
+            Opcode::Gtrr => {
+                self.registers[i.c] = if self.registers[i.a] > self.registers[i.b] {
+                    1
+                } else {
+                    0
+                }
+            }
+            Opcode::Eqir => self.registers[i.c] = if i.a == self.registers[i.b] { 1 } else { 0 },
+            Opcode::Eqri => self.registers[i.c] = if self.registers[i.a] == i.b { 1 } else { 0 },
+            Opcode::Eqrr => {
+                self.registers[i.c] = if self.registers[i.a] == self.registers[i.b] {
+                    1
+                } else {
+                    0
+                }
+            }
+        }
+    }
+}
+
+impl Iterator for Program {
+    type Item = Registers;
+
+    fn next(&mut self) -> Option<Self::Item> {
+        let ins = *self.instructions.get(self.registers[self.ip])?;
+        self.execute(&ins);
+        self.registers[self.ip] += 1;
+        Some(self.registers)
+    }
+}
+
+#[test]
+fn test_program() {
+    let mut program: Program = r"
+#ip 0
+seti 5 0 1
+seti 6 0 2
+addi 0 1 0
+addr 1 2 3
+setr 1 0 0
+seti 8 0 4
+seti 9 0 5
+    "
+    .parse()
+    .unwrap();
+
+    assert_eq!(program.next().unwrap(), [1, 5, 0, 0, 0, 0]);
+}
+
+#[derive(Clone, Copy)]
+struct Instruction {
+    opcode: Opcode,
+    a: usize,
+    b: usize,
+    c: usize,
+}
+
+#[derive(Clone, Copy)]
+enum Opcode {
+    Addr,
+    Addi,
+    Mulr,
+    Muli,
+    Banr,
+    Bani,
+    Borr,
+    Bori,
+    Setr,
+    Seti,
+    Gtir,
+    Gtri,
+    Gtrr,
+    Eqir,
+    Eqri,
+    Eqrr,
+}
+
+impl FromStr for Program {
+    type Err = Box<Error>;
+
+    fn from_str(s: &str) -> Result<Self, Self::Err> {
+        let mut lines = s.trim().lines();
+        let ip_re = Regex::new(r"^#ip (\d+)$").unwrap();
+        let ip = lines
+            .next()
+            .and_then(|l| ip_re.captures(l))
+            .and_then(|c| c.get(1))
+            .unwrap()
+            .as_str()
+            .parse()?;
+
+        let instructions = lines.map(|l| l.parse()).collect::<Result<_, _>>()?;
+
+        let registers = [0; 6];
+
+        Ok(Program {
+            ip,
+            instructions,
+            registers,
+        })
+    }
+}
+
+impl FromStr for Instruction {
+    type Err = Box<Error>;
+
+    fn from_str(s: &str) -> Result<Self, Self::Err> {
+        let mut s = s.split_whitespace();
+        let opcode = s.next().unwrap().parse()?;
+        let a = s.next().unwrap().parse()?;
+        let b = s.next().unwrap().parse()?;
+        let c = s.next().unwrap().parse()?;
+        Ok(Instruction { opcode, a, b, c })
+    }
+}
+
+impl FromStr for Opcode {
+    type Err = Box<Error>;
+
+    fn from_str(s: &str) -> Result<Self, Self::Err> {
+        let opcode = match s {
+            "addr" => Opcode::Addr,
+            "addi" => Opcode::Addi,
+            "mulr" => Opcode::Mulr,
+            "muli" => Opcode::Muli,
+            "banr" => Opcode::Banr,
+            "bani" => Opcode::Bani,
+            "borr" => Opcode::Borr,
+            "bori" => Opcode::Bori,
+            "setr" => Opcode::Setr,
+            "seti" => Opcode::Seti,
+            "gtir" => Opcode::Gtir,
+            "gtri" => Opcode::Gtri,
+            "gtrr" => Opcode::Gtrr,
+            "eqir" => Opcode::Eqir,
+            "eqri" => Opcode::Eqri,
+            "eqrr" => Opcode::Eqrr,
+            _ => unreachable!(),
+        };
+        Ok(opcode)
+    }
+}
+
+// OPCODES = {
+//   addr: ->(a, b, c) { ->(registers) { registers[c] = registers[a] + registers[b] } },
+//   addi: ->(a, b, c) { ->(registers) { registers[c] = registers[a] + b } },
+//   mulr: ->(a, b, c) { ->(registers) { registers[c] = registers[a] * registers[b] } },
+//   muli: ->(a, b, c) { ->(registers) { registers[c] = registers[a] * b } },
+//   banr: ->(a, b, c) { ->(registers) { registers[c] = registers[a] & registers[b] } },
+//   bani: ->(a, b, c) { ->(registers) { registers[c] = registers[a] & b } },
+//   borr: ->(a, b, c) { ->(registers) { registers[c] = registers[a] | registers[b] } },
+//   bori: ->(a, b, c) { ->(registers) { registers[c] = registers[a] | b } },
+//   setr: ->(a, b, c) { ->(registers) { registers[c] = registers[a] } },
+//   seti: ->(a, b, c) { ->(registers) { registers[c] = a } },
+//   gtir: ->(a, b, c) { ->(registers) { registers[c] = (a > registers[b]) ? 1 : 0 } },
+//   gtri: ->(a, b, c) { ->(registers) { registers[c] = (registers[a] > b) ? 1 : 0 } },
+//   gtrr: ->(a, b, c) { ->(registers) { registers[c] = (registers[a] > registers[b]) ? 1 : 0 } },
+//   eqir: ->(a, b, c) { ->(registers) { registers[c] = (a == registers[b]) ? 1 : 0 } },
+//   eqri: ->(a, b, c) { ->(registers) { registers[c] = (registers[a] == b) ? 1 : 0 } },
+//   eqrr: ->(a, b, c) { ->(registers) { registers[c] = (registers[a] == registers[b]) ? 1 : 0 } },
+// }