Day 13
[advent-of-code-17.git] / src / advent13 / advent13.ipynb
diff --git a/src/advent13/advent13.ipynb b/src/advent13/advent13.ipynb
new file mode 100644 (file)
index 0000000..cd129f3
--- /dev/null
@@ -0,0 +1,377 @@
+{
+ "cells": [
+  {
+   "cell_type": "code",
+   "execution_count": 1,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "{-# LANGUAGE NegativeLiterals #-}\n",
+    "{-# LANGUAGE FlexibleContexts #-}\n",
+    "{-# LANGUAGE OverloadedStrings #-}"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 4,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "import Data.Text (Text)\n",
+    "import qualified Data.Text as T\n",
+    "import qualified Data.Text.IO as TIO\n",
+    "\n",
+    "import Text.Megaparsec\n",
+    "import qualified Text.Megaparsec.Lexer as L\n",
+    "import Text.Megaparsec.Text (Parser)\n",
+    "\n",
+    "import qualified Data.Map.Strict as M\n",
+    "import Data.Map.Strict ((!))\n",
+    "\n",
+    "import qualified Data.Set as S\n",
+    "import qualified Control.Applicative as CA"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 49,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "scanner :: Integer -> Integer -> Integer -> Integer\n",
+    "scanner depth range t = \n",
+    "    let t' = (t + depth) `mod` ((range - 1) * 2)\n",
+    "    in if t' < range\n",
+    "       then t' \n",
+    "       else t' + (t' - range + 1) * -2"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 48,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "sc :: Parser ()\n",
+    "sc = L.space (skipSome spaceChar) CA.empty CA.empty\n",
+    "\n",
+    "lexeme  = L.lexeme sc\n",
+    "integer = lexeme L.integer\n",
+    "symb = L.symbol sc\n",
+    "\n",
+    "scannersP = many scannerP\n",
+    "\n",
+    "scannerP = (,) <$> integer <*> (symb \":\" *> integer)\n",
+    "\n",
+    "successfulParse :: Text -> [(Integer, Integer)]\n",
+    "successfulParse input = \n",
+    "        case parse scannersP \"input\" input of\n",
+    "                Left  err   -> [] -- TIO.putStr $ T.pack $ parseErrorPretty err\n",
+    "                Right scanners -> scanners"
+   ]
+  },
+  {
+   "cell_type": "markdown",
+   "metadata": {},
+   "source": [
+    "[0,1,2,3,4, 3, 2, 1,0,1,2,3] res = t' + x\n",
+    "[0,1,2,3,4, 5, 6, 7,0,1,2,3] t'\n",
+    "[           0, 1, 2          t' - len\n",
+    "           -2,-4,-6          x\n",
+    "\n",
+    "cycle is 5 + (5-2) = 8\n",
+    "\n",
+    "if t' <= 5 then t' else 5 - t' + 1\n",
+    "\n",
+    "\n",
+    "0 1 2 3 4 5 6 7 8 \n",
+    "S . . . . . . .\n",
+    ". S . . . . . .\n",
+    ". . S . . . . .\n",
+    ". . . S . . . .\n",
+    ". . . . S . . .\n",
+    ". . . . . S . .\n",
+    ". . . . . . S .\n",
+    ". . . . . . . S\n",
+    "\n"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 50,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "[0,1,2,3,4,3,2,1,0,1,2,3,4,3,2,1,0,1,2,3,4]"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "s50 = scanner 0 5\n",
+    "map s50 [0..20]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 51,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "[0,1,2,1,0,1,2,1,0,1,2,1,0,1,2,1,0,1,2,1,0]"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "s30 = scanner 0 3\n",
+    "map s30 [0..20]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 52,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "[3,2,1,0,1,2,3,2,1,0,1,2,3,2,1,0,1,2,3,2,1]"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "map (scanner 3 4) [0..20]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 53,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "[0,1,2,0]"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "[scanner 0 3 0, scanner 1 2 0, scanner 4 4 0, scanner 6 4 0]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 55,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "sample = [(0, 3), (1, 2), (4, 4), (6, 4)]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 58,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "24"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "sum $ map (uncurry (*)) $ filter (\\(d, r) -> scanner d r 0 == 0) sample "
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 61,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "part1 :: [(Integer, Integer)] -> Integer\n",
+    "part1 = sum . map (uncurry (*)) . filter (\\(d, r) -> scanner d r 0 == 0)"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 65,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "main :: IO ()\n",
+    "main = do \n",
+    "        text <- TIO.readFile \"../../data/advent13.txt\"\n",
+    "        let instrs = successfulParse text\n",
+    "        print $ part1 instrs"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 66,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "1904"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "main"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 68,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "scanify = map (uncurry scanner)"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 76,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "canPass scannersF t = all (\\s -> s t /= 0) scannersF"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 77,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "scs = scanify sample"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 82,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "10"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "head $ filter (canPass scs) [0..]"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 81,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "[2,1,2,2]"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "map (\\s -> s 10) scs"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 83,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "part2 scannerDefs = head $ filter (canPass scanners) [0..]\n",
+    "    where scanners = scanify scannerDefs"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 84,
+   "metadata": {},
+   "outputs": [],
+   "source": [
+    "main :: IO ()\n",
+    "main = do \n",
+    "        text <- TIO.readFile \"../../data/advent13.txt\"\n",
+    "        let instrs = successfulParse text\n",
+    "        print $ part1 instrs\n",
+    "        print $ part2 instrs"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 85,
+   "metadata": {},
+   "outputs": [
+    {
+     "data": {
+      "text/plain": [
+       "1904\n",
+       "3833504"
+      ]
+     },
+     "metadata": {},
+     "output_type": "display_data"
+    }
+   ],
+   "source": [
+    "main"
+   ]
+  },
+  {
+   "cell_type": "markdown",
+   "metadata": {},
+   "source": []
+  }
+ ],
+ "metadata": {
+  "kernelspec": {
+   "display_name": "Haskell",
+   "language": "haskell",
+   "name": "haskell"
+  },
+  "language_info": {
+   "codemirror_mode": "ihaskell",
+   "file_extension": ".hs",
+   "name": "haskell",
+   "version": "8.0.2"
+  }
+ },
+ "nbformat": 4,
+ "nbformat_minor": 2
+}