diff --git a/Project-02/main.py b/Project-02/main.py new file mode 100644 index 0000000..317dc70 --- /dev/null +++ b/Project-02/main.py @@ -0,0 +1,18 @@ +# This is a sample Python script for testing your TRIPLA parser. + +# In PyCharm press Umschalt+F10 to execute it. + +import triplayacc as yacc +import triplalex as lex + +def test_parser(name): + source = "\n".join(open(name).readlines()) + ast = yacc.parser.parse(source) # ,debug=True) + print("AST:") + print(ast) + +# Press the green button in the gutter to run the script. +if __name__ == '__main__': + test_parser('whileprograms/complex.while') + +# See PyCharm help at https://www.jetbrains.com/help/pycharm/ diff --git a/Project-02/parser.out b/Project-02/parser.out new file mode 100644 index 0000000..f0fda11 --- /dev/null +++ b/Project-02/parser.out @@ -0,0 +1,100 @@ +Created by PLY version 3.11 (http://www.dabeaz.com/ply) + +Grammar + +Rule 0 S' -> expression +Rule 1 expression -> CONST +Rule 2 expression -> WHILE expression DO LBRACE expression RBRACE + +Terminals, with rules where they appear + +CONST : 1 +DO : 2 +LBRACE : 2 +RBRACE : 2 +WHILE : 2 +error : + +Nonterminals, with rules where they appear + +expression : 2 2 0 + +Parsing method: LALR + +state 0 + + (0) S' -> . expression + (1) expression -> . CONST + (2) expression -> . WHILE expression DO LBRACE expression RBRACE + + CONST shift and go to state 2 + WHILE shift and go to state 3 + + expression shift and go to state 1 + +state 1 + + (0) S' -> expression . + + + +state 2 + + (1) expression -> CONST . + + $end reduce using rule 1 (expression -> CONST .) + DO reduce using rule 1 (expression -> CONST .) + RBRACE reduce using rule 1 (expression -> CONST .) + + +state 3 + + (2) expression -> WHILE . expression DO LBRACE expression RBRACE + (1) expression -> . CONST + (2) expression -> . WHILE expression DO LBRACE expression RBRACE + + CONST shift and go to state 2 + WHILE shift and go to state 3 + + expression shift and go to state 4 + +state 4 + + (2) expression -> WHILE expression . DO LBRACE expression RBRACE + + DO shift and go to state 5 + + +state 5 + + (2) expression -> WHILE expression DO . LBRACE expression RBRACE + + LBRACE shift and go to state 6 + + +state 6 + + (2) expression -> WHILE expression DO LBRACE . expression RBRACE + (1) expression -> . CONST + (2) expression -> . WHILE expression DO LBRACE expression RBRACE + + CONST shift and go to state 2 + WHILE shift and go to state 3 + + expression shift and go to state 7 + +state 7 + + (2) expression -> WHILE expression DO LBRACE expression . RBRACE + + RBRACE shift and go to state 8 + + +state 8 + + (2) expression -> WHILE expression DO LBRACE expression RBRACE . + + $end reduce using rule 2 (expression -> WHILE expression DO LBRACE expression RBRACE .) + DO reduce using rule 2 (expression -> WHILE expression DO LBRACE expression RBRACE .) + RBRACE reduce using rule 2 (expression -> WHILE expression DO LBRACE expression RBRACE .) + diff --git a/Project-02/parsetab.py b/Project-02/parsetab.py new file mode 100644 index 0000000..8ce2e8f --- /dev/null +++ b/Project-02/parsetab.py @@ -0,0 +1,32 @@ + +# parsetab.py +# This file is automatically generated. Do not edit. +# pylint: disable=W,C,R +_tabversion = '3.10' + +_lr_method = 'LALR' + +_lr_signature = 'CONST DO LBRACE RBRACE WHILEexpression : CONSTexpression : WHILE expression DO LBRACE expression RBRACE' + +_lr_action_items = {'CONST':([0,3,6,],[2,2,2,]),'WHILE':([0,3,6,],[3,3,3,]),'$end':([1,2,8,],[0,-1,-2,]),'DO':([2,4,8,],[-1,5,-2,]),'RBRACE':([2,7,8,],[-1,8,-2,]),'LBRACE':([5,],[6,]),} + +_lr_action = {} +for _k, _v in _lr_action_items.items(): + for _x,_y in zip(_v[0],_v[1]): + if not _x in _lr_action: _lr_action[_x] = {} + _lr_action[_x][_k] = _y +del _lr_action_items + +_lr_goto_items = {'expression':([0,3,6,],[1,4,7,]),} + +_lr_goto = {} +for _k, _v in _lr_goto_items.items(): + for _x, _y in zip(_v[0], _v[1]): + if not _x in _lr_goto: _lr_goto[_x] = {} + _lr_goto[_x][_k] = _y +del _lr_goto_items +_lr_productions = [ + ("S' -> expression","S'",1,None,None,None), + ('expression -> CONST','expression',1,'p_expression_const','triplayacc.py',28), + ('expression -> WHILE expression DO LBRACE expression RBRACE','expression',6,'p_expression_while','triplayacc.py',33), +] diff --git a/Project-02/syntax.py b/Project-02/syntax.py new file mode 100644 index 0000000..32097f6 --- /dev/null +++ b/Project-02/syntax.py @@ -0,0 +1,132 @@ + +# (c) Stephan Diehl, University of Trier, Germany, 2025 + +class EXPRESSION: + ppcount=0 + + def __init__(self): + self.pp=EXPRESSION.ppcount + EXPRESSION.ppcount=EXPRESSION.ppcount+1 + + def copy(self): + return EXPRESSION() + + def allNodes(self): + ret = [self] + for node in (self.__getattribute__(a) for a in self.__dict__.keys()): + if isinstance(node, EXPRESSION): + ret = ret + node.allNodes() + if isinstance(node, list): + for n in node: + if isinstance(n, EXPRESSION): + ret = ret + n.allNodes() + return ret + +class LET(EXPRESSION): + def __init__(self, declarations, body): + super().__init__() + self.declarations=declarations + self.body=body + + def __str__(self): return "let " \ + +','.join([ str(decl) for decl in self.declarations ]) \ + + " in " + str(self.body) + +class DECL(EXPRESSION): + def __init__(self, fname, params, body): + self.fname=fname + self.params=params + self.body=body + + def __str__(self): return self.fname+"(" \ + +','.join([ str(param) for param in self.params ]) \ + +"){ "+str(self.body)+" }" + +class CALL(EXPRESSION): + def __init__(self, fname, arguments): + super().__init__() + self.fname=fname + self.arguments=arguments + + def __str__(self): return self.fname+"(" \ + +','.join([ str(arg) for arg in self.arguments ]) +")" + + +class VAR(EXPRESSION): + def __init__(self,name): + super().__init__() + self.name=name + + def __str__(self): return self.name + +class BINOP(EXPRESSION): + def __init__(self,operator,arg1,arg2): + super().__init__() + self.operator=operator + self.arg1=arg1 + self.arg2=arg2 + + def __str__(self): return "("+str(self.arg1)+self.operator+str(self.arg2)+")" + +class CONST(EXPRESSION): + def __init__(self,value): + super().__init__() + self.value=value + + def __str__(self): return str(self.value) + +class ASSIGN(EXPRESSION): + def __init__(self, variable, expression): + super().__init__() + self.variable=variable + self.expression=expression + + def __str__(self): return self.variable.name+"="+str(self.expression) + +class SEQ(EXPRESSION): + def __init__(self, exp1, exp2): + super().__init__() + self.exp1=exp1 + self.exp2=exp2 + + def __str__(self): return str(self.exp1)+";"+str(self.exp2) + +class IF(EXPRESSION): + def __init__(self,condition,exp1,exp2): + super().__init__() + self.condition=condition + self.exp1=exp1 + self.exp2=exp2 + + def __str__(self): return "if "+str(self.condition)+" then { " \ + + str(self.exp1)+" } else { "+str(self.exp2)+" } " + +class DO(EXPRESSION): + def __init__(self,body,condition): + super().__init__() + self.body=body + self.condition=condition + + def __str__(self): return "do { "+str(self.body)+" } while "+str(self.condition) + +class WHILE(EXPRESSION): + def __init__(self,condition,body): + super().__init__() + self.condition=condition + self.body=body + + def __str__(self): return "while "+str(self.condition)+" do { "+str(self.body)+" }" + +# see https://stackoverflow.com/questions/51753937/python-pretty-print-nested-objects + +def pretty_print(clas, indent=0): + print(' ' * indent + type(clas).__name__ + ':') + indent += 4 + for k,v in clas.__dict__.items(): + if '__dict__' in dir(v): + pretty_print(v,indent) + else: + print(' ' * indent + k + ': ' + str(v)) + + + diff --git a/Project-02/triplalex.py b/Project-02/triplalex.py new file mode 100644 index 0000000..2da0402 --- /dev/null +++ b/Project-02/triplalex.py @@ -0,0 +1,46 @@ +# ------------------------------------------------------------ +# triplalex.py +# +# tokenizer for the TRIPLA parser +# ------------------------------------------------------------ +import ply.lex as lex + + +reserved = { + 'while' : 'WHILE', + 'do' : 'DO', +} + +# List of token names. This is always required +tokens = [ + 'CONST', + 'LBRACE', 'RBRACE' +]+list(reserved.values()) + +# Regular expression rules for simple tokens +t_LBRACE = r'\{' +t_RBRACE = r'\}' +t_WHILE = r'while' +t_DO = r'do' + +# A regular expression rule with some action code +def t_CONST(t): + r'\d+' + t.value = int(t.value) + return t + +# Define a rule so we can track line numbers +def t_newline(t): + r'\n+' + t.lexer.lineno += len(t.value) + +# A string containing ignored characters (spaces and tabs) +t_ignore = ' \t' + +# Error handling rule +def t_error(t): + print("Illegal character '%s'" % t.value[0]) + t.lexer.skip(1) + +# Build the lexer +lexer = lex.lex() diff --git a/Project-02/triplaprograms/argsParamsExample.tripla b/Project-02/triplaprograms/argsParamsExample.tripla new file mode 100644 index 0000000..0440a29 --- /dev/null +++ b/Project-02/triplaprograms/argsParamsExample.tripla @@ -0,0 +1,2 @@ +let a(x,y,z) {x} +in a(1,2,3) \ No newline at end of file diff --git a/Project-02/triplaprograms/complex.tripla b/Project-02/triplaprograms/complex.tripla new file mode 100644 index 0000000..a9ffacc --- /dev/null +++ b/Project-02/triplaprograms/complex.tripla @@ -0,0 +1,15 @@ +let +f1(b) { +if(b==0) then 0 else f1(b-1) +} +f2(a, b) { + if(a > b) then f1(a) else f1(b); + let g(c) { + a*b*c + } in g(a*b) +} +in +f1(10); f2(10, let max(a, b) { + if(a > b) then a else b + } + in max(20, 30)) \ No newline at end of file diff --git a/Project-02/triplaprograms/condition.tripla b/Project-02/triplaprograms/condition.tripla new file mode 100644 index 0000000..d6b92e6 --- /dev/null +++ b/Project-02/triplaprograms/condition.tripla @@ -0,0 +1 @@ +if 2 < x && x > 9 then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/defSemiExample.tripla b/Project-02/triplaprograms/defSemiExample.tripla new file mode 100644 index 0000000..9cae7f7 --- /dev/null +++ b/Project-02/triplaprograms/defSemiExample.tripla @@ -0,0 +1,4 @@ +let a(x) {x} + b(y) {y} + c(z) {z} +in a(1); b(2); c(3) \ No newline at end of file diff --git a/Project-02/triplaprograms/factorial.tripla b/Project-02/triplaprograms/factorial.tripla new file mode 100644 index 0000000..d3565c0 --- /dev/null +++ b/Project-02/triplaprograms/factorial.tripla @@ -0,0 +1,38 @@ +let + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } + fac(x) { + if (x == 1) then 1 + else fac(x-1)*x + } +in fac(3) \ No newline at end of file diff --git a/Project-02/triplaprograms/faulty-multiple-let.tripla b/Project-02/triplaprograms/faulty-multiple-let.tripla new file mode 100644 index 0000000..c8e9678 --- /dev/null +++ b/Project-02/triplaprograms/faulty-multiple-let.tripla @@ -0,0 +1 @@ +let n(a) {a} in n(5) + m(5) ; let m(a) {a+1} in m(5) \ No newline at end of file diff --git a/Project-02/triplaprograms/faulty_if.tripla b/Project-02/triplaprograms/faulty_if.tripla new file mode 100644 index 0000000..423c213 --- /dev/null +++ b/Project-02/triplaprograms/faulty_if.tripla @@ -0,0 +1 @@ +if (2 && 7 > 2) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/func.tripla b/Project-02/triplaprograms/func.tripla new file mode 100644 index 0000000..643f804 --- /dev/null +++ b/Project-02/triplaprograms/func.tripla @@ -0,0 +1,7 @@ +let func(a,b) { + do { + b = b + 1; + a = a - 1 + } while ( a > 0 && b != a ) + } +in func(10, 8) \ No newline at end of file diff --git a/Project-02/triplaprograms/ggT_euclid_iter.tripla b/Project-02/triplaprograms/ggT_euclid_iter.tripla new file mode 100644 index 0000000..f9507cb --- /dev/null +++ b/Project-02/triplaprograms/ggT_euclid_iter.tripla @@ -0,0 +1,12 @@ +let ggT(a, b) { + if (a == b) then + a + else + do { + if (a > b) then + a = a - b + else + b = b - a + } while (a != b); + a +} in ggT(3528, 3780) // result should be 252 \ No newline at end of file diff --git a/Project-02/triplaprograms/ggT_euclid_rec.tripla b/Project-02/triplaprograms/ggT_euclid_rec.tripla new file mode 100644 index 0000000..bc0fb08 --- /dev/null +++ b/Project-02/triplaprograms/ggT_euclid_rec.tripla @@ -0,0 +1,8 @@ +let ggT(a, b) { + if (a == b) then + a + else if (a > b) then + ggT(a-b, b) + else + ggT(b-a, a) +} in ggT(3528, 3780) // result should be 252 \ No newline at end of file diff --git a/Project-02/triplaprograms/invalidProgram.tripla b/Project-02/triplaprograms/invalidProgram.tripla new file mode 100644 index 0000000..cec7f8f --- /dev/null +++ b/Project-02/triplaprograms/invalidProgram.tripla @@ -0,0 +1,3 @@ +let f1(b) { if (b == 0) then 0 else f1(b-1) } + f2(a,b) { if (a > b) then f1(a) else f1(b) } +in f1(10); f2(10,-20) diff --git a/Project-02/triplaprograms/multiple-let-with-same-func-name.tripla b/Project-02/triplaprograms/multiple-let-with-same-func-name.tripla new file mode 100644 index 0000000..7faacfc --- /dev/null +++ b/Project-02/triplaprograms/multiple-let-with-same-func-name.tripla @@ -0,0 +1 @@ +let m(a){a} in m(5);let m(b){b+1} in m(5) \ No newline at end of file diff --git a/Project-02/triplaprograms/multiple-let.tripla b/Project-02/triplaprograms/multiple-let.tripla new file mode 100644 index 0000000..977d2ee --- /dev/null +++ b/Project-02/triplaprograms/multiple-let.tripla @@ -0,0 +1 @@ +let n(a) {a} in n(5) ; let m(a) {a+1} in n(5) + m(5) \ No newline at end of file diff --git a/Project-02/triplaprograms/or.tripla b/Project-02/triplaprograms/or.tripla new file mode 100644 index 0000000..76668c3 --- /dev/null +++ b/Project-02/triplaprograms/or.tripla @@ -0,0 +1 @@ +if(true||true==true) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/p1.tripla b/Project-02/triplaprograms/p1.tripla new file mode 100644 index 0000000..7c2fd1d --- /dev/null +++ b/Project-02/triplaprograms/p1.tripla @@ -0,0 +1,3 @@ +let g(a) { + a*a +} in g(5) \ No newline at end of file diff --git a/Project-02/triplaprograms/p2.tripla b/Project-02/triplaprograms/p2.tripla new file mode 100644 index 0000000..d5d519a --- /dev/null +++ b/Project-02/triplaprograms/p2.tripla @@ -0,0 +1,9 @@ +let f1(b) { + if (b==0) then 0 else f1(b-1) +} in f1(10) +/* +f2(a,b) { + if (a>b) then f1(a) else f1(b) +} +in f1(10); f2(10,20) +*/ \ No newline at end of file diff --git a/Project-02/triplaprograms/p3.tripla b/Project-02/triplaprograms/p3.tripla new file mode 100644 index 0000000..7b9b7af --- /dev/null +++ b/Project-02/triplaprograms/p3.tripla @@ -0,0 +1,14 @@ +let f1(b) { + if (b==0) then 0 else f1(b-1) +} +f2(a,b) { + if (a>b) then f1(a) else f1(b); + let g(c) { + a*b*c + } + in g(a*b) +} +in f1(10); f2(10, let max(a,b) { + if (a>b) then a else b + } + in max(20,30) ) \ No newline at end of file diff --git a/Project-02/triplaprograms/p4.tripla b/Project-02/triplaprograms/p4.tripla new file mode 100644 index 0000000..bcbd5f1 --- /dev/null +++ b/Project-02/triplaprograms/p4.tripla @@ -0,0 +1,4 @@ +let func(a,b) { + a = b + 1 + } +in func(10, 8) \ No newline at end of file diff --git a/Project-02/triplaprograms/p5.tripla b/Project-02/triplaprograms/p5.tripla new file mode 100644 index 0000000..2b8909d --- /dev/null +++ b/Project-02/triplaprograms/p5.tripla @@ -0,0 +1,9 @@ +let func(a, b) { + let func(a, b) { + a * b + } in + do { + b = b + 1 * func(3, 1); + a = a - 1 + } while ( a > 0 && b != a ) +} in func(10, 8) diff --git a/Project-02/triplaprograms/p6.tripla b/Project-02/triplaprograms/p6.tripla new file mode 100644 index 0000000..889263d --- /dev/null +++ b/Project-02/triplaprograms/p6.tripla @@ -0,0 +1,13 @@ +let f(a, b) { + if (a == 0) then + 2 + b + else + let g(a, c) { + a + c + b + } in 2 + g(a, b) +} g(c, d) { + if (c == 0) then + 1 + d + else + c * f(c - 1, d) +} in f (2, 3); g (3, 2) \ No newline at end of file diff --git a/Project-02/triplaprograms/side_effect.tripla b/Project-02/triplaprograms/side_effect.tripla new file mode 100644 index 0000000..4284c9f --- /dev/null +++ b/Project-02/triplaprograms/side_effect.tripla @@ -0,0 +1,5 @@ +let f(x, y) { + let g(x) { + y = x + 7 + } in x = g(5); y +} in f(1, 2) diff --git a/Project-02/triplaprograms/simple_dfa.tripla b/Project-02/triplaprograms/simple_dfa.tripla new file mode 100644 index 0000000..7209667 --- /dev/null +++ b/Project-02/triplaprograms/simple_dfa.tripla @@ -0,0 +1,4 @@ +let g(x, y) { + y = 3; + x +} in g(2) \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if.tripla b/Project-02/triplaprograms/simple_if.tripla new file mode 100644 index 0000000..59a484b --- /dev/null +++ b/Project-02/triplaprograms/simple_if.tripla @@ -0,0 +1 @@ +if (true) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_2.tripla b/Project-02/triplaprograms/simple_if_2.tripla new file mode 100644 index 0000000..02467fb --- /dev/null +++ b/Project-02/triplaprograms/simple_if_2.tripla @@ -0,0 +1 @@ +if (true && false) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_3.tripla b/Project-02/triplaprograms/simple_if_3.tripla new file mode 100644 index 0000000..66a4cb2 --- /dev/null +++ b/Project-02/triplaprograms/simple_if_3.tripla @@ -0,0 +1 @@ +if (true || false) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_4.tripla b/Project-02/triplaprograms/simple_if_4.tripla new file mode 100644 index 0000000..275be5e --- /dev/null +++ b/Project-02/triplaprograms/simple_if_4.tripla @@ -0,0 +1 @@ +if (1 > 2) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_5.tripla b/Project-02/triplaprograms/simple_if_5.tripla new file mode 100644 index 0000000..db2d395 --- /dev/null +++ b/Project-02/triplaprograms/simple_if_5.tripla @@ -0,0 +1 @@ +if (2 > 3 + 5) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_6.tripla b/Project-02/triplaprograms/simple_if_6.tripla new file mode 100644 index 0000000..65ddc34 --- /dev/null +++ b/Project-02/triplaprograms/simple_if_6.tripla @@ -0,0 +1 @@ +if (1 > 2 || 3 < 5) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/simple_if_7.tripla b/Project-02/triplaprograms/simple_if_7.tripla new file mode 100644 index 0000000..d7b1d54 --- /dev/null +++ b/Project-02/triplaprograms/simple_if_7.tripla @@ -0,0 +1 @@ +if (2 == 0 == false) then 1 else 0 \ No newline at end of file diff --git a/Project-02/triplaprograms/square.tripla b/Project-02/triplaprograms/square.tripla new file mode 100644 index 0000000..11e052a --- /dev/null +++ b/Project-02/triplaprograms/square.tripla @@ -0,0 +1,2 @@ +let square(x) { x*x } +in square(10) \ No newline at end of file diff --git a/Project-02/triplaprograms/validProgram.tripla b/Project-02/triplaprograms/validProgram.tripla new file mode 100644 index 0000000..51a1da2 --- /dev/null +++ b/Project-02/triplaprograms/validProgram.tripla @@ -0,0 +1,4 @@ +let mult(a,b) { a*b } + add(a,b) { let inc(a) { if (b!=0) then b=b-1;inc(a+1) else mult(a,1) } + in inc(a) } +in add(mult(2,3),add(4,5)) diff --git a/Project-02/triplaprograms/while.tripla b/Project-02/triplaprograms/while.tripla new file mode 100644 index 0000000..d7ecd34 --- /dev/null +++ b/Project-02/triplaprograms/while.tripla @@ -0,0 +1,7 @@ +let func(a,b) { + while ( a > 0 && b != a ) do { + b = b + 1; + a = a - 1 + } + } +in func(10, 8) \ No newline at end of file diff --git a/Project-02/triplaprograms/while_2.tripla b/Project-02/triplaprograms/while_2.tripla new file mode 100644 index 0000000..90ddb68 --- /dev/null +++ b/Project-02/triplaprograms/while_2.tripla @@ -0,0 +1,3 @@ +while (true) do { + 3 +} \ No newline at end of file diff --git a/Project-02/triplaprograms/wrapped-ggT.tripla b/Project-02/triplaprograms/wrapped-ggT.tripla new file mode 100644 index 0000000..95cf092 --- /dev/null +++ b/Project-02/triplaprograms/wrapped-ggT.tripla @@ -0,0 +1,8 @@ +let wrapper(a, b) { + let ggt(noneSense) { + if a == b then a + else + if a > b then wrapper(a-b, b) + else wrapper(b-a, a) + } in ggt(0) +} in wrapper(21, 49) \ No newline at end of file diff --git a/Project-02/triplaprograms/wrapper.tripla b/Project-02/triplaprograms/wrapper.tripla new file mode 100644 index 0000000..5902824 --- /dev/null +++ b/Project-02/triplaprograms/wrapper.tripla @@ -0,0 +1,9 @@ +let wrapper(number, threshold) { + let square(x) { + if x*x > threshold + then x + else x*x + } + in square(number) + } +in wrapper(4, 10) diff --git a/Project-02/triplayacc.py b/Project-02/triplayacc.py new file mode 100644 index 0000000..1492bc3 --- /dev/null +++ b/Project-02/triplayacc.py @@ -0,0 +1,45 @@ + +# ------------------------------------------------------------ +# triplayacc.py +# +# Yacc grammar of the TRIPLA language +''' Here an initial grammar + E -> while E do { E } + | CONST + + CONST: Positive, integer numbers = 0 | [1-9][0-9]* + +''' + +# Note: For LALR(1) left recursion is preferred +# ------------------------------------------------------------ + +import ply.yacc as yacc +import syntax as ast + +# Get the token map from the lexer. This is required. +from triplalex import tokens + +precedence = ( + +) + +def p_expression_const(p): + 'expression : CONST' + p[0] = ast.CONST(p[1]) + + +def p_expression_while(p): + 'expression : WHILE expression DO LBRACE expression RBRACE' + p[0] = ast.WHILE(p[2],p[5]) + +#def p_empty(p): +# 'empty :' +# pass + +# Error rule for syntax errors +def p_error(p): + print("Syntax error in input!") + +# Build the parser +parser = yacc.yacc() # debug=True diff --git a/Project-02/whileprograms/complex.while b/Project-02/whileprograms/complex.while new file mode 100644 index 0000000..1c09d16 --- /dev/null +++ b/Project-02/whileprograms/complex.while @@ -0,0 +1,2 @@ +while while 1 do { 2 } + do { while 3 do { 4 } } diff --git a/Project-02/whileprograms/simple.while b/Project-02/whileprograms/simple.while new file mode 100644 index 0000000..a019d6d --- /dev/null +++ b/Project-02/whileprograms/simple.while @@ -0,0 +1 @@ +while 1 do { 2 } \ No newline at end of file