summaryrefslogtreecommitdiff
path: root/next-lib/src/prelude/Formal.gf
blob: 2aa33d9eff86c1fd9167148b6011b85126f23213 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
resource Formal = open Prelude in {

-- to replace the old library Precedence

  oper
    Prec : PType ;
    TermPrec : Type = {s : Str ; p : Prec} ;

    mkPrec : Prec -> Str -> TermPrec = \p,s -> 
      {s = s ; p = p} ;

    top : TermPrec -> Str = usePrec 0 ;

    constant : Str -> TermPrec = mkPrec highest ;

    infixl : Prec -> Str -> (_,_ : TermPrec) -> TermPrec = \p,f,x,y ->
      mkPrec p (usePrec p x ++ f ++ usePrec (nextPrec p) y) ;
    infixr : Prec -> Str -> (_,_ : TermPrec) -> TermPrec = \p,f,x,y ->
      mkPrec p (usePrec (nextPrec p) x ++ f ++ usePrec p y) ;
    infixn : Prec -> Str -> (_,_ : TermPrec) -> TermPrec = \p,f,x,y ->
      mkPrec p (usePrec (nextPrec p) x ++ f ++ usePrec (nextPrec p) y) ;

-- auxiliaries, should not be needed so much

    usePrec : Prec -> TermPrec -> Str = \p,x ->
      case lessPrec x.p p of {
        True => parenth x.s ;
        False => parenthOpt x.s
      } ;

    parenth : Str -> Str = \s -> "(" ++ s ++ ")" ;
    parenthOpt : Str -> Str = \s -> variants {s ; "(" ++ s ++ ")"} ;

--.
-- low-level things: don't use

    Prec : PType = Predef.Ints 4 ;

    highest = 4 ;

    lessPrec : Prec -> Prec -> Bool = \p,q ->
      case <<p,q> : Prec * Prec> of {
        <3,4> | <2,3> | <2,4> => True ;
        <1,1> | <1,0> | <0,0> => False ;
        <1,_> | <0,_>         => True ;
        _ => False
        } ;

    nextPrec : Prec -> Prec = \p -> case <p : Prec> of {
      4 => 4 ; 
      n => Predef.plus n 1
      } ;

}