parser add optinoal parameters
This commit is contained in:
parent
30288731d3
commit
3d88a704ae
@ -18,6 +18,7 @@ public class Main {
|
||||
TestLoop loop = new TestLoop();
|
||||
TestMethodOverload overload = new TestMethodOverload();
|
||||
TestShenanigance shenanigance = new TestShenanigance();
|
||||
TestOptionalParameter optionalParameter = new TestOptionalParameter();
|
||||
|
||||
// constructing a basic class works
|
||||
assert empty != null;
|
||||
@ -50,8 +51,14 @@ public class Main {
|
||||
{
|
||||
assert malicious.cursedFormatting(i) == i;
|
||||
}
|
||||
// other syntactic sugar
|
||||
assert shenanigance.testAssignment() == 5;
|
||||
assert shenanigance.divEqual() == 234_343_000 / 4;
|
||||
assert shenanigance.testIf(5);
|
||||
// optional parameters
|
||||
assert optionalParameter.oneOptional() == 1;
|
||||
assert optionalParameter.oneOptional(2) == 2;
|
||||
assert optionalParameter.normalAndOptional(1) == 6;
|
||||
assert optionalParameter.normalAndOptional(1, 0, 0) == 1;
|
||||
}
|
||||
}
|
||||
|
10
Test/JavaSources/TestOptionalParameter.java
Normal file
10
Test/JavaSources/TestOptionalParameter.java
Normal file
@ -0,0 +1,10 @@
|
||||
class TestOptionalParameter {
|
||||
|
||||
int oneOptional(int p = 1) {
|
||||
return p;
|
||||
}
|
||||
|
||||
int normalAndOptional(int a, int b = 2, int c = 3) {
|
||||
return a + b + c;
|
||||
}
|
||||
}
|
@ -1,5 +1,5 @@
|
||||
{
|
||||
module Parser.JavaParser (parse, parseStatement, parseExpression) where
|
||||
module Parser.JavaParser (parse, parseStatement, parseExpression, parseMethod) where
|
||||
import Ast
|
||||
import Parser.Lexer
|
||||
}
|
||||
@ -7,6 +7,7 @@ import Parser.Lexer
|
||||
%name parse
|
||||
%name parseStatement statement
|
||||
%name parseExpression expression
|
||||
%name parseMethod classbodydeclarations
|
||||
%tokentype { Token }
|
||||
%error { parseError }
|
||||
%errorhandlertype explist
|
||||
@ -104,13 +105,13 @@ modifiers : modifier { }
|
||||
classbodydeclarations : classbodydeclaration {
|
||||
case $1 of
|
||||
ConstructorDecl constructor -> ([constructor], [], [])
|
||||
MethodDecl method -> ([], [method], [])
|
||||
MethodDecl method -> ([], (convertMethodDeclarationWithOptionals method), [])
|
||||
FieldDecls fields -> ([], [], fields)
|
||||
}
|
||||
| classbodydeclarations classbodydeclaration {
|
||||
case ($1, $2) of
|
||||
((constructors, methods, fields), ConstructorDecl constructor) -> ((constructors ++ [constructor]), methods, fields)
|
||||
((constructors, methods, fields), MethodDecl method) -> (constructors, (methods ++ [method]), fields)
|
||||
((constructors, methods, fields), MethodDecl method) -> (constructors, (methods ++ (convertMethodDeclarationWithOptionals method)), fields)
|
||||
((constructors, methods, fields), FieldDecls newFields) -> (constructors, methods, (fields ++ newFields))
|
||||
}
|
||||
|
||||
@ -136,7 +137,7 @@ constructordeclaration : constructordeclarator constructorbody { case $1 of (ide
|
||||
fielddeclaration : type variabledeclarators SEMICOLON { FieldDecls $ map (convertDeclarator $1) $2 }
|
||||
| modifiers type variabledeclarators SEMICOLON { FieldDecls $ map (convertDeclarator $2) $3 }
|
||||
|
||||
methoddeclaration : methodheader methodbody { case $1 of (returnType, (name, parameters)) -> MethodDecl (MethodDeclaration returnType name parameters $2) }
|
||||
methoddeclaration : methodheader methodbody { case $1 of (returnType, (name, (parameters, optionalparameters))) -> MethodDecl (MethodDeclarationWithOptionals returnType name parameters optionalparameters $2) }
|
||||
|
||||
block : LBRACKET RBRACKET { Block [] }
|
||||
| LBRACKET blockstatements RBRACKET { Block $2 }
|
||||
@ -166,6 +167,10 @@ methodbody : block { $1 }
|
||||
blockstatements : blockstatement { $1 }
|
||||
| blockstatements blockstatement { $1 ++ $2}
|
||||
|
||||
formalandoptionalparameterlist : formalparameterlist { ($1, []) }
|
||||
| formalparameterlist COMMA optionalparameterlist { ($1, $3) }
|
||||
| optionalparameterlist { ([], $1) }
|
||||
|
||||
formalparameterlist : formalparameter { [$1] }
|
||||
| formalparameterlist COMMA formalparameter { $1 ++ [$3] }
|
||||
|
||||
@ -175,8 +180,13 @@ explicitconstructorinvocation : THIS LBRACE RBRACE SEMICOLON { }
|
||||
classtypelist : classtype { }
|
||||
| classtypelist COMMA classtype { }
|
||||
|
||||
methoddeclarator : IDENTIFIER LBRACE RBRACE { ($1, []) }
|
||||
| IDENTIFIER LBRACE formalparameterlist RBRACE { ($1, $3) }
|
||||
methoddeclarator : IDENTIFIER LBRACE RBRACE { ($1, ([], [])) }
|
||||
| IDENTIFIER LBRACE formalandoptionalparameterlist RBRACE { ($1, $3) }
|
||||
|
||||
optionalparameterlist : optionalparameter { [$1] }
|
||||
| optionalparameterlist COMMA optionalparameter { $1 ++ [$3] }
|
||||
|
||||
optionalparameter : type variabledeclaratorid ASSIGN variableinitializer { OptionalParameter $1 $2 $4 }
|
||||
|
||||
primitivetype : BOOLEAN { "boolean" }
|
||||
| numerictype { $1 }
|
||||
@ -386,9 +396,9 @@ multiplicativeexpression : unaryexpression { $1 }
|
||||
|
||||
{
|
||||
|
||||
data MemberDeclaration = MethodDecl MethodDeclaration
|
||||
data MemberDeclaration = MethodDecl MethodDeclarationWithOptionals
|
||||
| ConstructorDecl ConstructorDeclaration
|
||||
| FieldDecls [VariableDeclaration]
|
||||
| FieldDecls [VariableDeclaration] deriving (Show)
|
||||
|
||||
data Declarator = Declarator Identifier (Maybe Expression)
|
||||
|
||||
@ -399,6 +409,22 @@ extractFunctionName :: Expression -> (Expression, Identifier)
|
||||
extractFunctionName (BinaryOperation NameResolution exp (Reference functionname)) = (exp, functionname)
|
||||
extractFunctionName (Reference functionname) = ((Reference "this"), functionname)
|
||||
|
||||
data OptionalParameter = OptionalParameter DataType Identifier Expression deriving (Show)
|
||||
data MethodDeclarationWithOptionals = MethodDeclarationWithOptionals DataType Identifier [ParameterDeclaration] [OptionalParameter] Statement deriving (Show)
|
||||
convertMethodDeclarationWithOptionals :: MethodDeclarationWithOptionals -> [MethodDeclaration]
|
||||
convertMethodDeclarationWithOptionals (MethodDeclarationWithOptionals returnType id param [] stmt) = [MethodDeclaration returnType id param stmt]
|
||||
convertMethodDeclarationWithOptionals (MethodDeclarationWithOptionals returnType id param (opt : optRest) stmt) = generateHelperMethod returnType id param opt : convertMethodDeclarationWithOptionals (generateBaseMethod returnType id param opt optRest stmt)
|
||||
convertOptionalParameter :: OptionalParameter -> ParameterDeclaration
|
||||
convertOptionalParameter (OptionalParameter dtype id exp) = ParameterDeclaration dtype id
|
||||
generateHelperMethod :: DataType -> Identifier -> [ParameterDeclaration] -> OptionalParameter -> MethodDeclaration
|
||||
generateHelperMethod returnType methodName params (OptionalParameter dtype id exp) =
|
||||
let references = ((map (\(ParameterDeclaration paramType ident) -> (Reference ident)) params) ++ [exp])
|
||||
methodcall = (MethodCall (Reference "this") methodName references)
|
||||
lastStatement = if returnType == "void" then StatementExpressionStatement methodcall else Return $ Just $ StatementExpressionExpression methodcall
|
||||
in MethodDeclaration returnType methodName params $ Block [lastStatement]
|
||||
generateBaseMethod :: DataType -> Identifier -> [ParameterDeclaration] -> OptionalParameter -> [OptionalParameter] -> Statement -> MethodDeclarationWithOptionals
|
||||
generateBaseMethod returnType methodName params (OptionalParameter dtype id exp) optRest stmt = MethodDeclarationWithOptionals returnType methodName (params ++ [ParameterDeclaration dtype id]) optRest stmt
|
||||
|
||||
parseError :: ([Token], [String]) -> a
|
||||
parseError (errortoken, expected) = error ("parse error on token: " ++ show errortoken ++ "\nexpected one of: " ++ show expected)
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user