aboutsummaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Helper.hs20
-rw-r--r--src/Parser.hs34
2 files changed, 53 insertions, 1 deletions
diff --git a/src/Helper.hs b/src/Helper.hs
index 695d63f..3617cfc 100644
--- a/src/Helper.hs
+++ b/src/Helper.hs
@@ -20,6 +20,9 @@ import Data.Maybe ( fromMaybe
, isNothing
)
import GHC.Generics ( Generic )
+import GHC.Real ( denominator
+ , numerator
+ )
import Text.Megaparsec
invalidProgramState :: a
@@ -370,7 +373,7 @@ humanifyString :: Expression -> Maybe String
humanifyString e = do
es <- unlistify e
str <- mapM binaryToChar' es
- pure str
+ pure $ "\"" <> str <> "\""
humanifyPair :: Expression -> Maybe String
humanifyPair e = do
@@ -381,6 +384,21 @@ humanifyPair e = do
---
+floatToRational :: Rational -> Expression
+floatToRational f = Abstraction
+ (Application (Application (Bruijn 0) (decimalToTernary p))
+ (decimalToTernary $ q - 1)
+ )
+ where
+ p = numerator f
+ q = denominator f
+
+floatToReal :: Rational -> Expression
+floatToReal f = Bruijn 0
+
+floatToComplex :: Rational -> Expression
+floatToComplex f = Bruijn 0
+
-- 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))]]]]
decimalToTernary :: Integer -> Expression
diff --git a/src/Parser.hs b/src/Parser.hs
index 57d6f58..a63b4a2 100644
--- a/src/Parser.hs
+++ b/src/Parser.hs
@@ -8,6 +8,7 @@ import Control.Monad ( ap
, void
)
import Data.Void
+import GHC.Real ( (%) )
import Helper
import Text.Megaparsec hiding ( parseTest )
import Text.Megaparsec.Char
@@ -135,6 +136,38 @@ parseNumeral = do
number :: Parser Integer
number = ap sign nat
+-- parsed float a.b to rational p/q
+convertToRational :: Integer -> Integer -> Rational
+convertToRational a b =
+ let denominator :: Integer
+ denominator = 10 ^ length (show b)
+ numerator = b + a * denominator
+ common = gcd numerator denominator
+ in (numerator `div` common) % (denominator `div` common)
+
+parseFloat :: Parser Expression
+parseFloat = do
+ _ <- string "(" <?> "float start"
+ num <- signedFloat <?> "signed float"
+ base <- try (oneOf "frc") <|> 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)
+ 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\\\"/")
@@ -201,6 +234,7 @@ parseSingleton =
let parseSingletonExpression =
parseBruijn
<|> try parseNumeral
+ <|> try parseFloat
<|> parseString
<|> try parseChar
<|> parseQuote