1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
|
#![allow(dead_code)]
#![allow(unused_variables)]
#![allow(unused_mut)]
use itertools::Itertools;
use std::cmp::max;
use std::env;
use std::fs::File;
use std::io::Read;
fn xmas(s: &[char], xy: &[(usize, usize)], m: &Vec<Vec<char>>) -> usize {
let mut count = 0;
let mx: usize = xy.iter().fold(0, |a, (x, y)| max(a, *x));
let my: usize = xy.iter().fold(0, |a, (x, y)| max(a, *y));
for r in 0..m.len() - my {
for c in 0..m[0].len() - mx {
if xy
.iter()
.enumerate()
.map(|(n, (x, y))| m[r + y][c + x] == s[n])
.all(|a| a)
{
count += 1;
}
}
}
count
}
fn cross_mas(m: &Vec<Vec<char>>) -> usize {
let mut count = 0;
for y in 1..m.len() - 1 {
for x in 1..m[0].len() - 1 {
if m[y][x] != 'A' {
continue;
}
let a = [
m[y - 1][x - 1],
m[y - 1][x + 1],
m[y + 1][x + 1],
m[y + 1][x - 1],
];
let mut m = ['M', 'M', 'S', 'S'];
for r in 0..4 {
if a == m {
count += 1;
break;
}
m.rotate_right(1);
}
}
}
count
}
fn main() {
let args: Vec<String> = env::args().collect();
let filename = if args.len() == 1 {
"in/".to_owned() + args[0].split('/').last().unwrap() + ".pzl"
} else {
args[1].clone()
};
let mut f = File::open(filename).expect("cannot open file");
let mut content = String::new();
f.read_to_string(&mut content).expect("cannot read file");
let lines = content.trim_end().split("\n");
let mut m: Vec<Vec<char>> = Vec::new();
for line in lines {
let mut l: Vec<char> = Vec::new();
for c in line.bytes() {
l.push(c as char)
}
m.push(l)
}
//println!("{:?}", m);
let ly = m.len();
let lx = m[0].len();
let s: Vec<char> = "XMAS".chars().collect();
let sr: Vec<char> = s.clone().into_iter().rev().collect();
let horiz: [(usize, usize); 4] = [(0, 0), (1, 0), (2, 0), (3, 0)];
let vert: [(usize, usize); 4] = [(0, 0), (0, 1), (0, 2), (0, 3)];
let diag1: [(usize, usize); 4] = [(0, 0), (1, 1), (2, 2), (3, 3)];
let diag2: [(usize, usize); 4] = [(3, 0), (2, 1), (1, 2), (0, 3)];
let res1: usize = [s, sr]
.into_iter()
.cartesian_product([horiz, vert, diag1, diag2].into_iter())
.map(|(s, d)| xmas(&s, &d, &m))
.sum();
let res2 = cross_mas(&m);
println!("res1: {}", res1);
println!("res2: {}", res2);
assert_eq!(res1, 2575);
assert_eq!(res2, 2041);
}
|