diff options
author | Marvin Borner | 2024-04-15 17:12:46 +0200 |
---|---|---|
committer | Marvin Borner | 2024-04-15 17:13:13 +0200 |
commit | bfdd0ef6897e42e03cefa4d43c8757ef09d96de2 (patch) | |
tree | 253509bc1a1ed34afc4a128952401921197fae7a /src | |
parent | 32f0891053cb9efe7b2987638a96395d2b9f9722 (diff) |
Added parsing and printing of complex numbers
Diffstat (limited to 'src')
-rw-r--r-- | src/Helper.hs | 51 | ||||
-rw-r--r-- | src/Parser.hs | 24 |
2 files changed, 66 insertions, 9 deletions
diff --git a/src/Helper.hs b/src/Helper.hs index 8ea5600..921604c 100644 --- a/src/Helper.hs +++ b/src/Helper.hs @@ -344,7 +344,9 @@ maybeHumanifyExpression e = <|> binaryToChar e <|> binaryToString e <|> ternaryToString e - <|> rationalToFloat e + <|> rationalToString e + <|> realToString e + <|> complexToString e <|> humanifyString e <|> humanifyList e <|> humanifyPair e @@ -398,8 +400,9 @@ floatToRational f = Abstraction floatToReal :: Rational -> Expression floatToReal = Abstraction . floatToRational -floatToComplex :: Rational -> Expression -floatToComplex f = Bruijn 0 +floatToComplex :: Rational -> Rational -> Expression +floatToComplex r i = Abstraction + $ Application (Application (Bruijn 0) (floatToReal r)) (floatToReal i) -- Dec to Bal3 in Bruijn encoding: reversed application with 0=>0; 1=>1; T=>2; end=>3 -- e.g. 0=0=[[[[3]]]]; 2=1T=[[[[2 (1 3)]]]] -5=T11=[[[[1 (1 (2 3))]]]] @@ -504,11 +507,10 @@ ternaryToDecimal e = do resolve' n resolve _ = Nothing -rationalToFloat :: Expression -> Maybe String -rationalToFloat (Abstraction (Application (Application (Bruijn 0) a) b)) = do +rationalToString :: Expression -> Maybe String +rationalToString (Abstraction (Application (Application (Bruijn 0) a) b)) = do n <- ternaryToDecimal a d <- ternaryToDecimal b - -- let (h, r) = properFraction (n % (d + 1)) Just $ show n <> "/" @@ -519,4 +521,39 @@ rationalToFloat (Abstraction (Application (Application (Bruijn 0) a) b)) = do "" ) <> ")" -rationalToFloat _ = Nothing +rationalToString _ = Nothing + +realToString :: Expression -> Maybe String +realToString (Abstraction e) = rationalToString e +realToString _ = Nothing + +complexToString :: Expression -> Maybe String +complexToString (Abstraction (Application (Application (Bruijn 0) (Abstraction (Abstraction (Application (Application (Bruijn 0) lr) rr)))) (Abstraction (Abstraction (Application (Application (Bruijn 0) li) ri))))) + = do + nlr <- ternaryToDecimal lr + drr <- ternaryToDecimal rr + nli <- ternaryToDecimal li + dri <- ternaryToDecimal ri + Just + $ show nlr + <> "/" + <> show (drr + 1) + <> " + " + <> show nli + <> "/" + <> show (dri + 1) + <> "i" + <> " (approx. " + <> (showFFloatAlt + (Just 8) + ((fromIntegral nlr) / (fromIntegral $ drr + 1) :: Double) + "" + ) + <> "+" + <> (showFFloatAlt + (Just 8) + ((fromIntegral nli) / (fromIntegral $ dri + 1) :: Double) + "" + ) + <> "i)" +complexToString _ = Nothing diff --git a/src/Parser.hs b/src/Parser.hs index a63b4a2..a24db6f 100644 --- a/src/Parser.hs +++ b/src/Parser.hs @@ -149,13 +149,12 @@ parseFloat :: Parser Expression parseFloat = do _ <- string "(" <?> "float start" num <- signedFloat <?> "signed float" - base <- try (oneOf "frc") <|> return 'f' + base <- try (oneOf "fr") <|> return 'f' _ <- string ")" <?> "float end" pure $ f base num where f 'f' = floatToRational f 'r' = floatToReal - f 'c' = floatToComplex -- TODO: imaginary f _ = invalidProgramState sign :: Parser (Rational -> Rational) sign = (char '-' >> return negate) <|> (char '+' >> return id) @@ -168,6 +167,26 @@ parseFloat = do signedFloat :: Parser Rational signedFloat = ap sign float +parseComplex :: Parser Expression +parseComplex = do + _ <- string "(" <?> "complex start" + real <- signedFloat <?> "signed complex" + _ <- char 'i' + imaginary <- signedFloat <?> "signed complex" + _ <- string ")" <?> "complex end" + pure $ floatToComplex real imaginary + where + sign :: Parser (Rational -> Rational) + sign = (char '-' >> return negate) <|> (char '+' >> return id) + float :: Parser Rational + float = do + a <- read <$> some digitChar <?> "digits" + _ <- char '.' <?> "float delimiter" + b <- read <$> some digitChar <?> "digits" + return $ convertToRational a b + signedFloat :: Parser Rational + signedFloat = ap sign float + specialEscape :: Parser Char specialEscape = choice (zipWith (\c r -> r <$ char c) "bnfrt\\\"/" "\b\n\f\r\t\\\"/") @@ -233,6 +252,7 @@ parseSingleton :: Parser Expression parseSingleton = let parseSingletonExpression = parseBruijn + <|> try parseComplex <|> try parseNumeral <|> try parseFloat <|> parseString |