125 lines
2.6 KiB
JavaScript
125 lines
2.6 KiB
JavaScript
#!/usr/bin/env node
|
|
|
|
|
|
var input = require('fs').readFileSync(process.argv[2]||'input.txt','utf8').split('\n').filter(i=>i);
|
|
//Make many versions of the data in different orientations
|
|
//All modes are an array of buffers. We will turn them into arrays of strings soon.
|
|
var mode0 = input.map(i=>Buffer.from(i));
|
|
//Width and height happen to be equal.. 140
|
|
var width = mode0[0].length;
|
|
var height = mode0.length;
|
|
//Transpose mode1
|
|
var mode1 = [];
|
|
for(var i=0;i<width;++i) { //Allocate
|
|
mode1.push(Buffer.alloc(height));
|
|
}
|
|
for(var i=0;i<height;++i) {
|
|
for(var j=0;j<width;++j) {
|
|
mode1[j][i]=mode0[i][j];
|
|
}
|
|
}
|
|
//Diaganal mode2
|
|
var mode2 = [];
|
|
for(var i=1;i<=width;++i) { //Allocate half
|
|
mode2.push(Buffer.alloc(i));
|
|
}
|
|
for(var i=width-1;i>0;--i) { //Allocate second half
|
|
mode2.push(Buffer.alloc(i));
|
|
}
|
|
var ri=0;
|
|
var rj=0;
|
|
var wi=0;
|
|
var wj=0;
|
|
try {
|
|
while(true) {
|
|
mode2[wi][wj]=mode0[ri][rj];
|
|
--ri;
|
|
++rj;
|
|
++wj;
|
|
if(mode2[wi].length==wj) { //This bit is simple
|
|
++wi;
|
|
wj=0;
|
|
}
|
|
if(ri<0) {
|
|
ri=rj
|
|
rj=0;
|
|
}
|
|
if(rj>=mode0.length) {
|
|
++ri; //Reverse
|
|
--rj; //Reverse
|
|
++ri; //Go down one
|
|
//Swap ri and rj
|
|
var temp=ri;
|
|
ri=rj;
|
|
rj=temp;
|
|
}
|
|
if(ri>=mode0.length) {
|
|
rj=(ri-(mode0.length-1));
|
|
ri=mode0.length-1;
|
|
}
|
|
}
|
|
} catch(e) {
|
|
//console.log('error',{ri,rj,wi,wj});
|
|
//Let it run. When we have an error we did the job
|
|
}
|
|
|
|
//Diagonal mode3
|
|
var mode3 = [];
|
|
for(var i=1;i<=width;++i) { //Allocate half
|
|
mode3.push(Buffer.alloc(i));
|
|
}
|
|
for(var i=width-1;i>0;--i) { //Allocate second half
|
|
mode3.push(Buffer.alloc(i));
|
|
}
|
|
var ri=0;
|
|
var rj=width-1;
|
|
var wi=0;
|
|
var wj=0;
|
|
try {
|
|
while(true) {
|
|
//console.log({ri,rj});
|
|
mode3[wi][wj]=mode0[ri][rj];
|
|
++ri;
|
|
++rj;
|
|
++wj;
|
|
if(mode3[wi].length==wj) { //This bit is simple
|
|
++wi;
|
|
wj=0;
|
|
}
|
|
if(rj>=width) {
|
|
--ri;//Reverse
|
|
--rj;//Reverse
|
|
++ri;//Get on new diaganol
|
|
rj=width-ri-1; // Go to other side of diaganol
|
|
ri=0; // Go to other side of diaganol
|
|
}
|
|
if(rj<0) {
|
|
ri=-rj;
|
|
rj=0;
|
|
}
|
|
if(ri>=width) {
|
|
--ri;//Reverse
|
|
--rj;//Reverse
|
|
--rj;//Get on new diaganol
|
|
ri=width-1-rj;
|
|
rj=0;
|
|
}
|
|
if(ri<0 || ri>=width || rj<0 || rj>=width) throw 'Out of bounds';
|
|
}
|
|
} catch(e) {
|
|
//console.log('Error mode3:',{ri,rj,wi,wj});
|
|
//Continue, it is filled;
|
|
}
|
|
|
|
|
|
var modes = [mode0,mode1,mode2,mode3].map(i=>i.map(i=>i.toString())); //Convert all into strings
|
|
var regex1 = /XMAS/g
|
|
var regex2 = /SAMX/g
|
|
|
|
var sum = modes.reduce((acc1,grid)=>acc1+grid.reduce((acc2,line)=>{
|
|
var match1 = line.match(regex1);
|
|
var match2 = line.match(regex2);
|
|
return acc2 + (match1?match1.length:0) + (match2?match2.length:0);
|
|
},0),0);
|
|
|
|
console.log('Result:',sum); |