module Text.Numeral.Language.POR
(
entry
, cardinal
, ordinal
, cardinal_struct
, ordinal_struct
, bounds
) where
import "base" Data.Function ( fix )
import "base" Data.Monoid ( (<>) )
import qualified "containers" Data.Map as M ( fromList, lookup )
import "this" Text.Numeral
import qualified "this" Text.Numeral.BigNum as BN
import "this" Text.Numeral.Misc ( dec )
import "this" Text.Numeral.Entry
import "text" Data.Text ( Text )
entry :: Entry
entry = emptyEntry
{ entIso639_1 = Just "pt"
, entIso639_2 = ["por"]
, entIso639_3 = Just "por"
, entNativeNames = ["Português"]
, entEnglishName = Just "Portuguese"
, entCardinal = Just Conversion
{ toNumeral = cardinal
, toStructure = cardinal_struct
}
, entOrdinal = Just Conversion
{ toNumeral = ordinal
, toStructure = ordinal_struct
}
}
cardinal :: (Integral a) => Inflection -> a -> Maybe Text
cardinal inf = cardinalRepr inf . cardinal_struct
ordinal :: (Integral a) => Inflection -> a -> Maybe Text
ordinal inf = ordinalRepr inf . ordinal_struct
cardinal_struct :: (Integral a) => a -> Exp
cardinal_struct = pos $ fix $ rule `combine` shortScale1_pt
where
rule = findRule ( 0, lit )
[ ( 11, add 10 L )
, ( 16, add 10 R )
, ( 20, mul 10 R L)
, ( 100, step 100 10 R L)
, (1000, step 1000 1000 R L)
]
(dec 6 1)
ordinal_struct :: (Integral a) => a -> Exp
ordinal_struct = pos $ fix $ rule `combine` shortScale1_pt
where
rule = findRule ( 0, lit )
[ ( 11, add 10 R )
, ( 20, mul 10 R L)
, ( 100, step 100 10 R L)
, (1000, step 1000 1000 R L)
]
(dec 6 1)
shortScale1_pt :: (Integral a) => Rule a
shortScale1_pt = mulScale1_es 3 3 R L BN.rule
where
mulScale1_es = mulScale_ $ \f m s _ -> masculineMul (f m) s
masculineMul x y = ChangeGender (Just Masculine) $ Mul x y
bounds :: (Integral a) => (a, a)
bounds = let x = dec 60000 1 in (negate x, x)
cardinalRepr :: Inflection -> Exp -> Maybe Text
cardinalRepr = render defaultRepr
{ reprValue = \inf n -> M.lookup n (syms inf)
, reprScale = shortScaleRepr
, reprAdd = Just (⊞)
, reprMul = Just (⊡)
, reprNeg = Just $ \_ _ -> "menos "
}
where
(Lit 10 ⊞ Lit n ) _
| n < 8 = "as"
| n == 8 = ""
| otherwise = "a"
(Lit _ ⊞ Lit 10) _ = ""
(_ ⊞ _ ) _ = " e "
(_ ⊡ Lit 10 ) _ = ""
(_ ⊡ Lit 100) _ = ""
(_ ⊡ _ ) _ = " "
syms inf =
M.fromList
[ (0, const "zero")
, (1, \c -> case c of
CtxAdd _ (Lit 10) _ -> "on"
_ | isFeminine inf -> "uma"
| otherwise -> "um"
)
, (2, \c -> case c of
CtxAdd _ (Lit 10) _ -> "do"
CtxMul _ (Lit 10) _ -> "vin"
CtxMul _ (Lit 100) _ -> "duz"
_ | isFeminine inf -> "duas"
| otherwise -> "dois"
)
, (3, \c -> case c of
CtxAdd _ (Lit 10) _ -> "tre"
CtxMul _ (Lit 10) _ -> "trin"
CtxMul _ (Lit 100) _ -> "trez"
_ -> "três"
)
, (4, \c -> case c of
CtxAdd _ (Lit 10) _ -> "cator"
CtxMul _ (Lit 10) _ -> "quaren"
_ -> "quatro"
)
, (5, \c -> case c of
CtxAdd _ (Lit 10) _ -> "quin"
CtxMul _ (Lit 10) _ -> "cinquen"
CtxMul _ (Lit 100) _ -> "quin"
_ -> "cinco"
)
, (6, \c -> case c of
CtxMul _ (Lit 10) _ -> "sessen"
_ -> "seis"
)
, (7, \c -> case c of
CtxMul _ (Lit 10) _ -> "seten"
_ -> "sete"
)
, (8, \c -> case c of
CtxMul _ (Lit 10) _ -> "oiten"
_ -> "oito"
)
, (9, \c -> case c of
CtxMul _ (Lit 10) _ -> "noven"
_ -> "nove"
)
, (10, \c -> case c of
CtxAdd R (Lit _) _ -> "ze"
CtxMul R (Lit 2) _ -> "te"
CtxMul R (Lit _) _ -> "ta"
_ -> "dez"
)
, (100, \c -> case c of
CtxAdd {} -> "cento"
CtxMul _ (Lit n) _
| n <= 3 -> if isFeminine inf then "entas" else "entos"
| n == 5 -> if isFeminine inf then "hentas" else "hentos"
| n <= 9 -> if isFeminine inf then "centas" else "centos"
| otherwise -> "cem"
_ -> "cem"
)
, (1000, const "mil")
]
ordinalRepr :: Inflection -> Exp -> Maybe Text
ordinalRepr = render defaultRepr
{ reprValue = \inf n -> M.lookup n (syms inf)
, reprScale = shortScaleRepr
, reprAdd = Just (⊞)
, reprMul = Just (⊡)
, reprNeg = Just $ \_ _ -> "menos "
}
where
(Lit _ ⊞ Lit 10) _ = ""
(_ ⊞ _ ) _ = " "
(_ ⊡ Lit 10 ) _ = ""
(_ ⊡ Lit 100) _ = ""
(_ ⊡ _ ) _ = " "
syms inf =
M.fromList
[ (0, const "zero")
, (1, \c -> case c of
_ -> "primeir" <> postFix
)
, (2, \c -> case c of
CtxMul _ (Lit 10) _ -> "vi"
CtxMul _ (Lit 100) _ -> "du"
_ -> "segund" <> postFix
)
, (3, \c -> case c of
CtxMul _ (Lit 10) _ -> "tri"
CtxMul _ (Lit 100) _ -> "tre"
_ -> "terceir" <> postFix
)
, (4, \c -> case c of
CtxMul _ (Lit 10) _ -> "quadra"
CtxMul _ (Lit 100) _ -> "quadrin"
_ -> "quart" <> postFix
)
, (5, \c -> case c of
CtxMul _ (Lit 10) _ -> "qüinqua"
CtxMul _ (Lit 100) _ -> "qüin"
_ -> "quint" <> postFix
)
, (6, \c -> case c of
CtxMul _ (Lit 10) _ -> "sexa"
CtxMul _ (Lit 100) _ -> "sex"
_ -> "sext" <> postFix
)
, (7, \c -> case c of
CtxMul _ (Lit 10) _ -> "septua"
CtxMul _ (Lit 100) _ -> "setin"
_ -> "sétim" <> postFix
)
, (8, \c -> case c of
CtxMul _ (Lit 10) _ -> "octo"
CtxMul _ (Lit 100) _ -> "octin"
_ -> "oitav" <> postFix
)
, (9, \c -> case c of
CtxMul _ (Lit 10) _ -> "nona"
CtxMul _ (Lit 100) _ -> "non"
_ -> "non" <> postFix
)
, (10, \c -> case c of
CtxAdd R (Lit _) _ -> "ze"
CtxMul R (Lit _) _
| isOutside R c -> "gésim" <> postFix
| otherwise -> "gésimo"
_ | isOutside R c -> "décim" <> postFix
| otherwise -> "décimo"
)
, (100, \c -> case c of
CtxAdd {} -> "cento"
CtxMul _ (Lit n) _
| not (n `elem` [2,3,6]) -> "gentésim" <> postFix
_ -> "centésim" <> postFix
)
, (1000, const $ "milésim" <> postFix)
]
where
postFix = if isFeminine inf
then if isSingular inf
then "a"
else "as"
else if isSingular inf
then "o"
else "os"
shortScaleRepr :: Inflection -> Integer -> Integer -> Exp -> Ctx Exp -> Maybe Text
shortScaleRepr =
BN.scaleRepr (BN.quantityName "ilhão" "ilhões")
[(4, BN.forms "quatr" "quator" "quator" "quatra" "quatri")]