working i think

This commit is contained in:
Thorn Avery 2019-07-23 12:31:43 +12:00
commit 32b4e078ea
3 changed files with 92 additions and 0 deletions

4
.gitignore vendored Normal file
View File

@ -0,0 +1,4 @@
*.swp
spiral
*.hi
*.o

30
README.md Normal file
View File

@ -0,0 +1,30 @@
# Spiral
bad attempts at solving interview questions
## The Problem - Verbatim
Write a small program which:
accepts on the command line an odd number N
outputs a sequence of numbers corresponding to the following steps:
the numbers 1 through N^2 are written in a grid
the first number in the sequence is the number in the center of the grid
the subsequent numbers are found by spiraling out clockwise, starting to the right
For example, for N = 3 we have the grid:
1 2 3
4 5 6
7 8 9
So we start with 5, head right to 6, then down to 9, left through 8 and 7, up through 4 and 1 and finally right through 2 and 3. This gives the output:
5, 6, 9, 8, 7, 4, 1, 2, 3, end
For N=5 the output should be:
13, 14, 19, 18, 17, 12, 7, 8, 9, 10, 15, 20, 25, 24, 23, 22, 21, 16, 11, 6, 1, 2, 3, 4, 5, end
IMPORTANT: your solution should not make use of arrays or matrices of numbers. If you are unable to determine a way to solve it without arrays/matrices then a solution with them is better than no solution.
## Compiling and Running
```
ghc -02 -Wall Spiral.hs -o spiral
spiral
```

58
spiral.hs Normal file
View File

@ -0,0 +1,58 @@
import System.IO
data Incarnation = S Bool Bool Int (Int,Int) Int Int
seed :: Int -> Int
seed n = 1 + (h * (n+1))
where h = (div n 2)
lineage :: Int -> [Int]
lineage n = take (n*n) $ futures (atom n)
atom :: Int -> Incarnation
atom n = S False True 1 (1,0) (seed n) n
xor :: Bool -> Bool -> Bool
xor a b = (a || b) && (not (a && b))
futures :: Incarnation -> [Int]
futures self@(S _ _ _ _ l _) =
(l:(futures (evolve self)))
divine :: Incarnation -> Int
divine (S v s _ _ l n) = l `sign` val
where
sign = if s then (+) else (-)
val = if v then n else 1
evolve :: Incarnation -> Incarnation
evolve i@(S v s cd (so,sn) _ b)
| cd > 1 = (S v s (cd-1) (so,sn) (divine i) b)
| otherwise =
(S (not v) (s `xor` v) (cs ns) ns (divine i) b)
where
ns = (intuit v (so,sn))
cs = (if v then fst else snd)
intuit :: Bool -> (Int,Int) -> (Int,Int)
intuit True (a,b) = ((a+1),b)
intuit _ (a,b) = (a,(b+1))
-- blurgh io
-- bloating the program making me import stuff >:(
main :: IO ()
main = do
putStr "destinies to observe: "
hFlush stdout
args <- getLine
mapM_ putStrLn
$ map (\n -> ("n=" ++ (show n) ++ " ~ ")
++ (if (aura n)
then (show (lineage (read n)))
else "[ soul contains invalid aura ]"))
(words args)
aura :: String -> Bool
aura s = foldr (&&) True
(map (`elem` ['0'..'9']) s)