Year 2015 Day 9 Part 2
This commit is contained in:
parent
c46d3d911b
commit
cf3a81fa62
|
@ -1,4 +1,4 @@
|
|||
# Year 2016 Day 9
|
||||
# Year 2015 Day 9
|
||||
|
||||
This day provides our first example of a graph traversal problem. We'll use a
|
||||
`Choose` based effectful breath first search to identify all the possible paths
|
||||
|
@ -210,11 +210,9 @@ lengths.
|
|||
|
||||
```idris
|
||||
shortestPath : Has (Reader DistanceMap) fs => Has (Except String) fs =>
|
||||
(paths : List (List Location)) -> Eff fs (List Location, Integer)
|
||||
(paths : List (List Location, Integer)) -> Eff fs (List Location, Integer)
|
||||
shortestPath paths = do
|
||||
lens <- traverse pathLen paths
|
||||
let pairs = zip paths lens
|
||||
shortest pairs Nothing
|
||||
shortest paths Nothing
|
||||
where
|
||||
shortest : List (a, Integer) -> (acc : Maybe (a, Integer))
|
||||
-> Eff fs (a, Integer)
|
||||
|
@ -228,6 +226,27 @@ shortestPath paths = do
|
|||
else shortest xs (Just y)
|
||||
```
|
||||
|
||||
Calculate the longest path from a list of paths by recursively comparing
|
||||
lengths.
|
||||
|
||||
```idris
|
||||
longestPath : Has (Reader DistanceMap) fs => Has (Except String) fs =>
|
||||
(paths : List (List Location, Integer)) -> Eff fs (List Location, Integer)
|
||||
longestPath paths = do
|
||||
longest paths Nothing
|
||||
where
|
||||
longest : List (a, Integer) -> (acc : Maybe (a, Integer))
|
||||
-> Eff fs (a, Integer)
|
||||
longest [] acc = note "No paths" acc
|
||||
longest (x :: xs) acc =
|
||||
case acc of
|
||||
Nothing => longest xs (Just x)
|
||||
Just y =>
|
||||
if (snd x) > (snd y)
|
||||
then longest xs (Just x)
|
||||
else longest xs (Just y)
|
||||
```
|
||||
|
||||
## Part Functions
|
||||
|
||||
### Part 1
|
||||
|
@ -236,7 +255,8 @@ Parse our locations, turn them into a `DistanceMap`, load that into our reader,
|
|||
generate our paths, then find the one with the shortest length.
|
||||
|
||||
```idris
|
||||
part1 : Eff (PartEff String) (Integer, ())
|
||||
part1 :
|
||||
Eff (PartEff String) (Integer, (DistanceMap, List (List Location, Integer)))
|
||||
part1 = do
|
||||
locations <- map lines (askAt "input") >>= traverse parseLocationPair
|
||||
info "Locations: \{show locations}"
|
||||
|
@ -246,13 +266,29 @@ part1 = do
|
|||
paths <- map Prelude.toList allPaths
|
||||
trace "Paths: \{show paths}"
|
||||
info "Found \{show $ length paths} paths"
|
||||
(path, len) <- shortestPath paths
|
||||
distances <- traverse pathLen paths
|
||||
let pairs = zip paths distances
|
||||
(path, len) <- shortestPath pairs
|
||||
info "Shortest Path: \{show path} \{show len}"
|
||||
pure (len, ())
|
||||
pure (len, (distance_map, pairs))
|
||||
```
|
||||
|
||||
### Part 2
|
||||
|
||||
Feed the locations back into a longest path function
|
||||
|
||||
```idris
|
||||
part2 : (DistanceMap, List (List Location, Integer))
|
||||
-> Eff (PartEff String) Integer
|
||||
part2 (distance_map, pairs) = do
|
||||
runReader distance_map {fs = Reader DistanceMap :: PartEff String} $ do
|
||||
(path, len) <- longestPath pairs
|
||||
info "Longest Path: \{show path} \{show len}"
|
||||
pure len
|
||||
```
|
||||
|
||||
<!-- idris
|
||||
public export
|
||||
day9 : Day
|
||||
day9 = First 9 part1
|
||||
day9 = Both 9 part1 part2
|
||||
-->
|
||||
|
|
Loading…
Reference in a new issue