1
0
forked from GitHub/gf-core

cleanup in the python export

This commit is contained in:
peter.ljunglof
2012-06-27 23:27:01 +00:00
parent 8444821759
commit 871eb6eabc

View File

@@ -1,4 +1,5 @@
---------------------------------------------------------------------- ----------------------------------------------------------------------
-- |
-- Module : PGFtoPython -- Module : PGFtoPython
-- Maintainer : Peter Ljunglöf -- Maintainer : Peter Ljunglöf
-- --
@@ -11,6 +12,8 @@ import PGF.CId
import PGF.Data import PGF.Data
import qualified PGF.Macros as M import qualified PGF.Macros as M
import GF.Data.Operations
import qualified Data.Array.IArray as Array import qualified Data.Array.IArray as Array
import qualified Data.Set as Set import qualified Data.Set as Set
import qualified Data.Map as Map import qualified Data.Map as Map
@@ -18,91 +21,96 @@ import qualified Data.IntMap as IntMap
import Data.List (intersperse) import Data.List (intersperse)
pgf2python :: PGF -> String pgf2python :: PGF -> String
pgf2python pgf = "# -*- coding: UTF-8 -*-\n" ++ pgf2python pgf = ("# -*- coding: UTF-8 -*-" ++++
"# This file was automatically generated by GF\n\n" ++ "# This file was automatically generated by GF" +++++
showCId name ++ " = " ++ grammar ++ "\n" showCId name +++ "=" +++
pyDict 1 pyStr id [
("flags", pyDict 2 pyCId pyLiteral (Map.assocs (gflags pgf))),
("abstract", pyDict 2 pyStr id [
("name", pyCId name),
("start", pyCId start),
("flags", pyDict 3 pyCId pyLiteral (Map.assocs (aflags abs))),
("funs", pyDict 3 pyCId pyAbsdef (Map.assocs (funs abs)))
]),
("concretes", pyDict 2 pyCId pyConcrete (Map.assocs cncs))
] ++ "\n")
where where
name = absname pgf name = absname pgf
start = M.lookStartCat pgf start = M.lookStartCat pgf
abs = abstract pgf abs = abstract pgf
cncs = concretes pgf cncs = concretes pgf
grammar = pyDict 1 [(qs "abstract", pyDict 2 [(qs "name", qcid name),
(qs "start", qcid start),
(qs "flags", pyDict 0 [(qcid k, lit2py v) |
(k, v) <- Map.toList (aflags abs)]),
(qs "funs", pyDict 3 [(qcid f, absdef2py def) |
(f, def) <- Map.assocs (funs abs)])]),
(qs "concretes", pyDict 2 [(qcid cname, concrete2py cnc) |
(cname, cnc) <- Map.assocs cncs])]
absdef2py :: (Type, Int, Maybe [Equation], Double) -> String pyAbsdef :: (Type, Int, Maybe [Equation], Double) -> String
absdef2py (typ, _, _, _) = pyTuple 0 [qcid cat, pyList 0 (map qcid args)] pyAbsdef (typ, _, _, _) = pyTuple 0 id [pyCId cat, pyTuple 0 pyCId args]
where (args, cat) = M.catSkeleton typ where (args, cat) = M.catSkeleton typ
lit2py :: Literal -> String pyLiteral :: Literal -> String
lit2py (LStr s) = qs s pyLiteral (LStr s) = pyStr s
lit2py (LInt n) = show n pyLiteral (LInt n) = show n
lit2py (LFlt d) = show d pyLiteral (LFlt d) = show d
concrete2py :: Concr -> String pyConcrete :: Concr -> String
concrete2py cnc = pyDict 3 [(qs "flags", pyDict 0 [(qcid k, lit2py v) | (k, v) <- Map.toList (cflags cnc)]), pyConcrete cnc = pyDict 3 pyStr id [
(qs "prods", pyDict 4 [(show cat, pyList 0 (map frule2py (Set.toList set))) | ("flags", pyDict 0 pyCId pyLiteral (Map.assocs (cflags cnc))),
(cat, set) <- IntMap.toList (productions cnc)]), ("printnames", pyDict 4 pyCId pyStr (Map.assocs (printnames cnc))),
(qs "cfuns", pyList 4 [ffun2py f | f <- Array.elems (cncfuns cnc)]), ("lindefs", pyDict 4 pyCat (pyTuple 0 pyFun) (IntMap.assocs (lindefs cnc))),
(qs "seqs", pyList 4 [seq2py s | s <- Array.elems (sequences cnc)]), ("productions", pyDict 4 pyCat pyProds (IntMap.assocs (productions cnc))),
(qs "ccats", pyDict 4 [(qcid cat, pyTuple 0 [show start, show end]) | ("cncfuns", pyDict 4 pyFun pyCncFun (Array.assocs (cncfuns cnc))),
(cat, CncCat start end _) <- Map.assocs (cnccats cnc)]), ("sequences", pyDict 4 pySeq pySymbols (Array.assocs (sequences cnc))),
(qs "size", show (totalCats cnc))] ("cnccats", pyDict 4 pyCId pyCncCat (Map.assocs (cnccats cnc))),
("size", show (totalCats cnc))
]
where pyProds prods = pyTuple 5 pyProduction (Set.toList prods)
pyCncCat (CncCat start end _) = pyTuple 0 pyCat [start..end]
pyCncFun (CncFun f lins) = pyTuple 0 id [pyTuple 0 pySeq (Array.elems lins), pyCId f]
pySymbols syms = pyTuple 0 pySymbol (Array.elems syms)
frule2py :: Production -> String pyProduction :: Production -> String
frule2py (PApply funid args) = pyTuple 0 [show funid, pyList 0 (map parg2py args)] pyProduction (PCoerce arg) = pyTuple 0 id [pyStr "", pyTuple 0 pyCat [arg]]
frule2py (PCoerce arg) = show arg pyProduction (PApply funid args) = pyTuple 0 id [pyFun funid, pyTuple 0 pyPArg args]
where pyPArg (PArg [] fid) = pyCat fid
pyPArg (PArg hypos fid) = pyTuple 0 pyCat (fid : map snd hypos)
parg2py :: PArg -> String pySymbol :: Symbol -> String
parg2py (PArg [] fid) = show fid pySymbol (SymCat n l) = pyTuple 0 show [n, l]
parg2py (PArg hypos fid) = pyTuple 0 (show fid : map (show . snd) hypos) pySymbol (SymLit n l) = pyDict 0 pyStr id [("lit", pyTuple 0 show [n, l])]
pySymbol (SymVar n l) = pyDict 0 pyStr id [("var", pyTuple 0 show [n, l])]
ffun2py :: CncFun -> String pySymbol (SymKS ts) = prTList "," (map pyStr ts)
ffun2py (CncFun f lins) = pyTuple 0 [pyList 0 (map show (Array.elems lins)), qcid f] pySymbol (SymKP ts alts) = pyDict 0 pyStr id [("pre", pyTuple 0 pyStr ts), ("alts", pyTuple 0 alt2py alts)]
where alt2py (Alt ps ts) = pyTuple 0 (pyTuple 0 pyStr) [ps, ts]
seq2py :: Array.Array DotPos Symbol -> String
seq2py seq = pyList 0 [sym2py s | s <- Array.elems seq]
sym2py :: Symbol -> String
sym2py (SymCat n l) = pyTuple 0 [show n, show l]
sym2py (SymLit n l) = pyDict 0 [(qs "lit", pyTuple 0 [show n, show l])]
sym2py (SymVar n l) = pyDict 0 [(qs "var", pyTuple 0 [show n, show l])]
sym2py (SymKS ts) = join "," (map qs ts)
sym2py (SymKP ts alts) = pyDict 0 [(qs "pre", pyList 0 (map show ts)),
(qs "alts", pyList 0 (map alt2py alts))]
where alt2py (Alt ps ts) = pyTuple 0 [pyList 0 (map show ps), pyList 0 (map show ts)]
---------------------------------------------------------------------- ----------------------------------------------------------------------
-- python helpers -- python helpers
pyDict :: Int -> [(String, String)] -> String pyDict :: Int -> (k -> String) -> (v -> String) -> [(k, v)] -> String
pyDict n xys = "{" ++ indent n ++ join ("," ++ indent n) [x ++ ":" ++ y | (x, y) <- xys] ++ indent n ++ "}" pyDict n pk pv [] = "{}"
pyDict n pk pv kvlist = prCurly (pyIndent n ++ prTList ("," ++ pyIndent n) (map pyKV kvlist) ++ pyIndent n)
where pyKV (k, v) = pk k ++ ":" ++ pv v
pyList :: Int -> [String] -> String pyList :: Int -> (v -> String) -> [v] -> String
pyList n xs = "[" ++ indent n ++ join ("," ++ indent n) xs ++ indent n ++ "]" pyList n pv [] = "[]"
pyList n pv xs = prBracket (pyIndent n ++ prTList ("," ++ pyIndent n) (map pv xs) ++ pyIndent n)
pyTuple :: Int -> [String] -> String pyTuple :: Int -> (v -> String) -> [v] -> String
pyTuple n [x] = "(" ++ indent n ++ x ++ "," ++ indent n ++ ")" pyTuple n pv [] = "()"
pyTuple n xs = "(" ++ indent n ++ join ("," ++ indent n) xs ++ indent n ++ ")" pyTuple n pv [x] = prParenth (pyIndent n ++ pv x ++ "," ++ pyIndent n)
pyTuple n pv xs = prParenth (pyIndent n ++ prTList ("," ++ pyIndent n) (map pv xs) ++ pyIndent n)
qs :: String -> String pyCat :: Int -> String
qs s = "u\"" ++ qs' s pyCat n = pyStr ('C' : show n)
where qs' ('"':s) = "\\\"" ++ qs' s
qs' ('\\':s) = "\\\\" ++ qs' s
qs' (c:s) = c : qs' s
qs' [] = "\""
qcid :: CId -> String pyFun :: Int -> String
qcid = qs . showCId pyFun n = pyStr ('F' : show n)
indent :: Int -> String pySeq :: Int -> String
indent n | n > 0 = "\n" ++ replicate n ' ' pySeq n = pyStr ('S' : show n)
| otherwise = ""
join :: String -> [String] -> String pyStr :: String -> String
join a bs = concat (intersperse a bs) pyStr s = 'u' : prQuotedString s
pyCId :: CId -> String
pyCId = pyStr . showCId
pyIndent :: Int -> String
pyIndent n | n > 0 = "\n" ++ replicate n ' '
| otherwise = ""