Year 2015 Day 8 Part 2
This commit is contained in:
parent
9a16de8be7
commit
ca07f2995e
|
@ -199,7 +199,7 @@ string = do
|
||||||
pure xs
|
pure xs
|
||||||
```
|
```
|
||||||
|
|
||||||
## Running a parser
|
### Running a parser
|
||||||
|
|
||||||
Run a parser, with some debug logging, by peeling the parsing effects of of the
|
Run a parser, with some debug logging, by peeling the parsing effects of of the
|
||||||
type. The order is important here, remember that function composition "runs"
|
type. The order is important here, remember that function composition "runs"
|
||||||
|
@ -284,6 +284,23 @@ runParser x str = do
|
||||||
lazyRights (Right x :: xs) = x :: lazyRights xs
|
lazyRights (Right x :: xs) = x :: lazyRights xs
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Escaping characters
|
||||||
|
|
||||||
|
This is much more boring the the parsing, we just do simple recursive pattern
|
||||||
|
matching on the characters of the provided string, escaping `"` and `\`, and
|
||||||
|
surround the resulting string with quotes.
|
||||||
|
|
||||||
|
```idris
|
||||||
|
escape : String -> String
|
||||||
|
escape str = "\"\{pack . escape' . unpack $ str}\""
|
||||||
|
where
|
||||||
|
escape' : List Char -> List Char
|
||||||
|
escape' [] = []
|
||||||
|
escape' ('"' :: xs) = '\\' :: '"' :: escape' xs
|
||||||
|
escape' ('\\' :: xs) = '\\' :: '\\' :: escape' xs
|
||||||
|
escape' (x :: xs) = x :: escape' xs
|
||||||
|
```
|
||||||
|
|
||||||
## Part Functions
|
## Part Functions
|
||||||
|
|
||||||
### Part 1
|
### Part 1
|
||||||
|
@ -293,7 +310,7 @@ possible failures by sequencing the `List (Maybe String)` into a
|
||||||
`Maybe (List String)`, and the compute the difference in character counts.
|
`Maybe (List String)`, and the compute the difference in character counts.
|
||||||
|
|
||||||
```idris
|
```idris
|
||||||
part1 : Eff (PartEff String) (Int, ())
|
part1 : Eff (PartEff String) (Int, List String)
|
||||||
part1 = do
|
part1 = do
|
||||||
inputs <- map lines $ askAt "input"
|
inputs <- map lines $ askAt "input"
|
||||||
outputs <- traverse (runParser string) inputs
|
outputs <- traverse (runParser string) inputs
|
||||||
|
@ -301,11 +318,34 @@ part1 = do
|
||||||
| _ => throw "Some strings failed to parse"
|
| _ => throw "Some strings failed to parse"
|
||||||
let difference =
|
let difference =
|
||||||
sum $ zipWith (\x, y => strLength x - strLength y) inputs outputs
|
sum $ zipWith (\x, y => strLength x - strLength y) inputs outputs
|
||||||
pure (difference, ())
|
pure (difference, inputs)
|
||||||
|
```
|
||||||
|
|
||||||
|
### Part 2
|
||||||
|
|
||||||
|
Map our character escaping function over our input string and compute the
|
||||||
|
difference in character counts.
|
||||||
|
|
||||||
|
Make a little stop along the way to ensure that escape -> parse round trips
|
||||||
|
without changing the content of the string.
|
||||||
|
|
||||||
|
```idris
|
||||||
|
part2 : List String -> Eff (PartEff String) Int
|
||||||
|
part2 inputs = do
|
||||||
|
let outputs = map escape inputs
|
||||||
|
Just reversed_outputs <- map sequence . traverse (runParser string) $ outputs
|
||||||
|
| _ => throw "Reversing escaping of the inputs failed"
|
||||||
|
unless (all id $ zipWith (==) inputs reversed_outputs) $ do
|
||||||
|
debug . delay . joinBy "\n" . map show . filter (\(x, y, z) => x /= z) $
|
||||||
|
zip3 inputs outputs reversed_outputs
|
||||||
|
throw "Parsed outputs were not identical to inputs"
|
||||||
|
let difference =
|
||||||
|
sum $ zipWith (\x, y => strLength y - strLength x) inputs outputs
|
||||||
|
pure difference
|
||||||
```
|
```
|
||||||
|
|
||||||
<!-- idris
|
<!-- idris
|
||||||
public export
|
public export
|
||||||
day8 : Day
|
day8 : Day
|
||||||
day8 = First 8 part1
|
day8 = Both 8 part1 part2
|
||||||
-->
|
-->
|
||||||
|
|
Loading…
Reference in a new issue