summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrew Cady <d@jerkface.net>2020-12-29 14:56:54 -0500
committerAndrew Cady <d@jerkface.net>2020-12-29 14:56:54 -0500
commit3b57f59955968a3c3288ba3e8fb79114b78bc370 (patch)
tree6068fa8878b8c4ae3fca7f64afa615b36e9c5af0
parentab981deb57eedc35ec7bbb4f20e9deecd307123c (diff)
fixed
-rwxr-xr-xshelf.hs61
1 files changed, 30 insertions, 31 deletions
diff --git a/shelf.hs b/shelf.hs
index 61710e8..8389d63 100755
--- a/shelf.hs
+++ b/shelf.hs
@@ -1,6 +1,6 @@
1#!/usr/bin/env stack 1#!/usr/bin/env stack
2{- stack script --resolver lts-16.27 --install-ghc 2{- stack script --resolver lts-16.27 --install-ghc
3 --ghc-options -Wall --ghc-options -Wno-unused-imports -} 3 --ghc-options -Wall --ghc-options -Wno-unused-imports --ghc-options -Wno-name-shadowing -}
4{-# language NoImplicitPrelude #-} 4{-# language NoImplicitPrelude #-}
5{-# language DuplicateRecordFields #-} 5{-# language DuplicateRecordFields #-}
6import Rebase.Prelude 6import Rebase.Prelude
@@ -9,50 +9,49 @@ import Control.Lens
9import Data.Ratio 9import Data.Ratio
10import Text.Printf 10import Text.Printf
11 11
12toCarpenter :: RealFrac a => a -> (Int, Int, Ratio Int) 12formatFeet :: RealFrac a => a -> String
13toCarpenter l = (feet, div r 32, mod r 32 % 32) where 13formatFeet 0 = "0"
14 (feet, r) = divMod (round $ l * 32) (32 * 12) 14formatFeet l = unwords $ toList (feet f) ++ toList (inches i n d)
15 15 where
16feetAndInches :: RealFrac a => a -> String 16 feet 0 = Nothing
17feetAndInches l = case toCarpenter l of 17 feet f = Just $ printf "%d'" f
18 (0,0,0) -> "0 feet 0 inches" 18 inches 0 0 _ = Nothing
19 (f,i,t) -> showUnit "foot" "feet" (f % 1) ++ 19 inches i 0 _ = Just $ printf "%d\"" i
20 (if f > 0 && (i%1 + t) > 0 then " " else "") ++ 20 inches 0 n d = Just $ printf "%d/%d\"" n d
21 showUnit "inch" "inches" (i % 1 + t) 21 inches i n d = Just $ printf "%d %d/%d\"" i n d
22 where 22
23 showUnit _ _ 0 = "" 23 n = numerator t
24 showUnit s m n = printf "%s %s" (showVal n) $ if n <= 1 then s else m 24 d = denominator t
25 showVal v | d == 1 = show n 25 (f, i, t) = toCarpenter l
26 | v < 1 = printf "%d/%d" n d 26
27 | otherwise = printf "%d and %d/%d" (div n d) (mod n d) d 27 toCarpenter :: RealFrac a => a -> (Int, Int, Ratio Int)
28 where (n,d) = (numerator v, denominator v) 28 toCarpenter l = (feet, div r 32, mod r 32 % 32) where
29 (feet, r) = divMod (round $ l * 32) (32 * 12)
29 30
30type Inches = Rational 31type Inches = Rational
31 32
32boardLength, boardThickness, kickerHeight, numShelves, numHorizontals, availableSpace :: Inches 33boardLength, boardThickness, kickerHeight, availableSpace :: Inches
33boardLength = 6 * 12 34boardLength = 6 * 12
34boardThickness = 5/8 35boardThickness = 5/8
35kickerHeight = 4 36kickerHeight = 4
36numShelves = 5 37numHorizontals, numShelves :: Int
38numShelves = length shelves
37 39
38numHorizontals = numShelves + 1 40numHorizontals = numShelves + 1
39availableSpace = boardLength - kickerHeight - numHorizontals * boardThickness 41availableSpace = boardLength - kickerHeight - (toRational numHorizontals) * boardThickness
40 42
41shelves :: [Rational] 43shelves :: [Rational]
42shelves = kickerHeight : map (* availableSpace) [2%9, 2%9, 2%9, 1%6, 1%6] 44shelves = map (* availableSpace) [2%9, 2%9, 2%9, 1%6, 1%6]
43 45
44positions :: [Inches] 46positions, positions' :: [Inches]
45positions = map (+ boardThickness) $ map sum $ tails shelves 47positions = map sum $ (tail . inits) $ concatMap (: [boardThickness]) $ kickerHeight : shelves
46 48
47positions' = map (boardLength -) positions 49positions' = map (boardLength -) positions
48 50
49main :: IO () 51main :: IO ()
50main = do 52main = do
51 _ <- return $ assert $ sum shelves == 1 53 void $ return $ assert $ sum shelves == 1
52 print shelves 54 mapM_ putStrLn $ formatFeet <$> positions
53 print positions 55 putStrLn ""
54 print $ map (fromRational :: Rational -> Float) positions 56 mapM_ putStrLn $ formatFeet <$> positions'
55 print positions'
56 print $ map (fromRational :: Rational -> Float) positions'
57 mapM_ putStrLn $ feetAndInches <$> positions'
58 return () 57 return ()