Skip to content

Commit

Permalink
scope
Browse files Browse the repository at this point in the history
  • Loading branch information
mantarias committed May 10, 2024
1 parent 1adc9c7 commit d7e1f3e
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 52 deletions.
2 changes: 1 addition & 1 deletion src/main/antlr4/dk/aau/cs_24_sw_4_16/carl/CARL.g4
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,7 @@ primary
ifStatement : 'if' expression block ( 'else if' expression block )* ( 'else' block )? ;
whileLoop : 'while' expression block ;
returnStatement : 'return' expression? ;
block : '{' (statement | expression)* '}' ;
block : '{' (statement)* '}' ;
arrayAccess : IDENTIFIER '[' expression ']' ('[' expression ']')*;
propertyAccess : structType '.' IDENTIFIER ('.' IDENTIFIER)? ;
coordinateDeclaration : 'var' IDENTIFIER ':' 'coord' '=' '(' expression ',' expression ')' ;//Virker ikke nødvendigt, hvorfor ikke bare bruge arrayAcces?
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,29 @@ public static void print(FunctionCallNode node, Stack<HashMap<String, AstNode>>
if (argument instanceof StatementNode) {
toPrint.append(((StatementNode) argument).getNode()).append(" ");
} else if (argument instanceof IdentifierNode) {
if (scopes.getFirst().containsKey(argument.toString())) {
toPrint.append(scopes.getFirst().get(argument.toString()).toString()).append(" ");
} else {
for (int i = activeScope.getLast(); i < scopes.size(); i++) {
int towards = !activeScope.isEmpty() ? activeScope.getLast() : 0;
boolean found = false;
for (int i = scopes.size() - 1; i >= towards; i--) {
if (scopes.get(i).containsKey(argument.toString())) {
toPrint.append(scopes.get(i).get(argument.toString()).toString()).append(" ");
found = true;
break;
}
}

if (!found) {
int from = 0;
if (!activeScope.isEmpty()) {
from = activeScope.getFirst();
} else {
from = scopes.size() - 1;
}
for (int i = from; i >= 0; i--) {
if (scopes.get(i).containsKey(argument.toString())) {
toPrint.append(scopes.get(i).get(argument.toString()).toString()).append(" ");
toPrint.append(scopes.getFirst().get(argument.toString()).toString()).append(" ");
}
}

}

} else if (argument instanceof FloatNode) {
Expand Down
109 changes: 83 additions & 26 deletions src/main/java/dk/aau/cs_24_sw_4_16/carl/Interpreter/Interpreter.java
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ public Interpreter() {
tileInformationWall = new HashMap<>();
scopes = new Stack<>();
activeScope = new ArrayDeque<>();
activeScope.push(0);
// activeScope.push(0);
scopes.add(vTable);
rooms = new ArrayList<>();
}
Expand All @@ -45,8 +45,8 @@ public AstNode visit(AstNode node) {
}
return node;
}
public AstNode roomCall(MethodCallNode node)
{

public AstNode roomCall(MethodCallNode node) {
if (node.getPropertyAccessContext().getIdentifiers().get(0).toString().equals("size")) {
return new IntNode(rooms.size());
} else if (node.getPropertyAccessContext().getIdentifiers().get(0).toString().equals("get")) {
Expand All @@ -63,6 +63,7 @@ public AstNode roomCall(MethodCallNode node)
}
throw new RuntimeException("method call went wrong");
}

public AstNode visit(MethodCallNode node) {
HashMap<String, HashMap<String, AstNode>> list;
switch (node.getPropertyAccessContext().getList()) {
Expand Down Expand Up @@ -230,35 +231,70 @@ public void visit(IfStatementNode node) {

public AstNode getVariable(IdentifierNode node) {
// for (HashMap<String, AstNode> vTable : scopes) {
if (scopes.getFirst().containsKey(node.getIdentifier())) {
return scopes.getFirst().get(node.getIdentifier());
}

for (int i = activeScope.getLast(); i < scopes.size(); i++) {
int towards =!activeScope.isEmpty() ? activeScope.getLast() : 0;
for (int i = scopes.size() - 1; i >= towards; i--) {
if (scopes.get(i).containsKey(node.getIdentifier())) {
return scopes.get(i).get(node.getIdentifier());
}
}
int from = 0;
if (!activeScope.isEmpty()) {
from = activeScope.getFirst();
} else {
from = scopes.size() - 1;
}
for (int i = from; i >= 0; i--) {
if (scopes.get(i).containsKey(node.getIdentifier())) {
return scopes.get(i).get(node.getIdentifier());
}
}
// if (scopes.getFirst().containsKey(node.getIdentifier())) {
// return scopes.getFirst().get(node.getIdentifier());
// }
throw new RuntimeException("could not find the variable " + node.getIdentifier());
}

public void visit(AssignmentNode node) {
for (HashMap<String, AstNode> vTable : scopes) {
if (vTable.containsKey(node.getIdentifier().toString())) {
AstNode nodeToChange = vTable.get(node.getIdentifier().toString());
int towards = !activeScope.isEmpty() ? activeScope.getLast() : 0;
for (int i = scopes.size() - 1; i >= towards; i--) {
if (scopes.get(i).containsKey(node.getIdentifier().getIdentifier())) {
// if (vTable.containsKey(node.getIdentifier().toString())) {
AstNode nodeToChange = scopes.get(i).get(node.getIdentifier().toString());
AstNode toChange = node.getValue();
replaceValue(nodeToChange, toChange);
return;
}
}
int from = 0;
if (!activeScope.isEmpty()) {
from = activeScope.getFirst();
} else {
from = scopes.size() - 1;
}
for (int i = from; i >= 0; i--) {
if (scopes.get(i).containsKey(node.getIdentifier())) {
AstNode nodeToChange = scopes.get(i).get(node.getIdentifier().toString());
AstNode toChange = node.getValue();
replaceValue(nodeToChange, toChange);
return;
}
}
// if (scopes.getFirst().containsKey(node.getIdentifier().toString())) {
// AstNode nodeToChange = scopes.getFirst().get(node.getIdentifier().toString());
// AstNode toChange = node.getValue();
// replaceValue(nodeToChange, toChange);
// return;
// }

throw new RuntimeException("Variable '" + node.getIdentifier() + "' has not been defined yet.");
}


public void visit(VariableDeclarationNode node) {

if (!idExists(node.getIdentifier().toString())) {
if (!scopes.getLast().containsKey(node.getIdentifier().getIdentifier())) {
// if (!idExists(node.getIdentifier().toString())) {

AstNode toChange = node.getValue();
if (toChange instanceof FunctionCallNode) {
Expand Down Expand Up @@ -289,7 +325,7 @@ public void visit(VariableDeclarationNode node) {
}

} else {
throw new RuntimeException("variable " + node.getIdentifier() + " already exists");
throw new RuntimeException("variable " + node.getIdentifier() + " already exists in the current scope");
}
}

Expand All @@ -307,9 +343,9 @@ public AstNode visit(ArrayAccessNode node) {

return ((ArrayNode) getVariable(node.getIdentifier()))
.get(
node.getIndices().stream().mapToInt(
astNode -> evaluate_int(astNode).getValue()
).toArray()
node.getIndices().stream().mapToInt(
astNode -> evaluate_int(astNode).getValue()
).toArray()
);
}

Expand Down Expand Up @@ -338,31 +374,31 @@ public void visit(ArrayAssignmentNode node) {
((ArrayNode) getVariable(node.getIdentifier())).set(value, indices);
}

private IntNode evaluate_int(AstNode node){
private IntNode evaluate_int(AstNode node) {
if (node instanceof BinaryOperatorNode) {
return (IntNode) visit((BinaryOperatorNode) node);
} else if (node instanceof IdentifierNode) {

var value = getVariable((IdentifierNode) node);
if (value instanceof IntNode )
if (value instanceof IntNode)
return (IntNode) value;
else
throw new RuntimeException("Type mismatch: Expected " + ((IdentifierNode) node).getIdentifier() + " to be an int, got " + value.getClass());
} else if (node instanceof FunctionCallNode){
} else if (node instanceof FunctionCallNode) {
var value = visit((FunctionCallNode) node);
if (value instanceof IntNode )
if (value instanceof IntNode)
return (IntNode) value;
else
throw new RuntimeException("Type mismatch: Expected " + ((FunctionCallNode) node).getFunctionName().getIdentifier() + "() to return an int, got " + value.getClass());
} else if (node instanceof RelationsAndLogicalOperatorNode){
} else if (node instanceof RelationsAndLogicalOperatorNode) {
var value = visit((RelationsAndLogicalOperatorNode) node);
if (value instanceof IntNode )
if (value instanceof IntNode)
return (IntNode) value;
else
throw new RuntimeException("Type mismatch: " + ((RelationsAndLogicalOperatorNode) node).operator + " operator doesn't return an int");
} else if (node instanceof IntNode) {
return (IntNode) node;
} else if (node instanceof ExpressionNode){
} else if (node instanceof ExpressionNode) {
return evaluate_int(((ExpressionNode) node).getNode());
} else {
throw new RuntimeException("Expected an integer, got " + node.getClass());
Expand All @@ -380,15 +416,36 @@ public void visit(ArrayDefinitionNode node) {

private boolean idExists(String id) {
boolean found = false;
if (scopes.getFirst().containsKey(id)) {
found = true;
int towards = !activeScope.isEmpty() ? activeScope.getLast() : 0;
for (int i = scopes.size() - 1; i >= towards; i--) {
if (scopes.get(i).containsKey(id)) {
found = true;
}
}

for (int i = activeScope.getLast(); i < scopes.size(); i++) {
int from = 0;
if (!activeScope.isEmpty()) {
from = activeScope.getFirst();
} else {
from = scopes.size() - 1;
}
for (int i = from; i >= 0; i--) {
if (scopes.get(i).containsKey(id)) {
found = true;
}
}
// if (scopes.getFirst().containsKey(id)) {
// found = true;
// }

// if (scopes.getFirst().containsKey(id)) {
// found = true;
// }
//
// for (int i = activeScope.getLast(); i < scopes.size(); i++) {
// if (scopes.get(i).containsKey(id)) {
// found = true;
// }
// }

return found;
}
Expand Down
36 changes: 16 additions & 20 deletions test.carl
Original file line number Diff line number Diff line change
@@ -1,22 +1,18 @@
var Orc : enemy = {
var difficulty : int = 1
var health : int = 200
var symbol : string= "O"
var x:int =2

fn plus (y:int)-> int{
var help : int = x + y
return help
}
var Goblin : enemy ={
var difficulty : int = 1
var health : int = 500
var symbol : string= "O"
}
var Goblin2 : enemy ={
var difficulty : int = 1
var health : int = 500
var symbol : string= "O"
}
var Goblin3 : enemy ={
var difficulty : int = 1
var health : int = 500
var symbol : string= "O"
}
var test : int = 1..enemy.size()

var test : string = "test"
print(test)

if true {
var x:int = 5 //
var test : int = 5
test = 6
var result : int = plus(2)
print(result)
}
print(test)

0 comments on commit d7e1f3e

Please sign in to comment.