for in syntax

This commit is contained in:
nub31
2025-10-22 18:32:45 +02:00
parent 0f96e83e44
commit fd1f4a0130
8 changed files with 172 additions and 25 deletions

View File

@@ -40,6 +40,10 @@ public record BreakNode(List<Token> Tokens) : TerminalStatementNode(Tokens);
public record WhileNode(List<Token> Tokens, ExpressionNode Condition, BlockNode Body) : StatementNode(Tokens);
public record ForSliceNode(List<Token> Tokens, string ElementName, string? IndexName, ExpressionNode Target, BlockNode Body) : StatementNode(Tokens);
public record ForConstArrayNode(List<Token> Tokens, string ElementName, string? IndexName, ExpressionNode Target, BlockNode Body) : StatementNode(Tokens);
public record DeferNode(List<Token> Tokens, StatementNode Statement) : StatementNode(Tokens);
#endregion

View File

@@ -234,6 +234,51 @@ public sealed class TypeChecker
return new WhileNode(statement.Tokens, condition, body);
}
private StatementNode CheckFor(ForSyntax forSyntax)
{
var target = CheckExpression(forSyntax.Target);
switch (target.Type)
{
case NubSliceType sliceType:
{
using (BeginScope())
{
Scope.DeclareVariable(new Variable(forSyntax.ElementName, sliceType.ElementType));
if (forSyntax.IndexName != null)
{
Scope.DeclareVariable(new Variable(forSyntax.IndexName, new NubIntType(false, 64)));
}
var body = CheckBlock(forSyntax.Body);
return new ForSliceNode(forSyntax.Tokens, forSyntax.ElementName, forSyntax.IndexName, target, body);
}
}
case NubConstArrayType constArrayType:
{
using (BeginScope())
{
Scope.DeclareVariable(new Variable(forSyntax.ElementName, constArrayType.ElementType));
if (forSyntax.IndexName != null)
{
Scope.DeclareVariable(new Variable(forSyntax.IndexName, new NubIntType(false, 64)));
}
var body = CheckBlock(forSyntax.Body);
return new ForConstArrayNode(forSyntax.Tokens, forSyntax.ElementName, forSyntax.IndexName, target, body);
}
}
default:
{
throw new TypeCheckerException(Diagnostic
.Error($"For statement not supported for type {target.Type}")
.At(forSyntax)
.Build());
}
}
}
private FuncPrototypeNode CheckFuncPrototype(FuncPrototypeSyntax statement)
{
var parameters = new List<FuncParameterNode>();
@@ -332,8 +377,8 @@ public sealed class TypeChecker
private ArrayInitializerNode CheckArrayInitializer(ArrayInitializerSyntax expression, NubType? _)
{
var elementType = ResolveType(expression.ElementType);
var type = new NubArrayType(elementType);
var capacity = CheckExpression(expression.Capacity);
var type = new NubArrayType(elementType);
return new ArrayInitializerNode(expression.Tokens, type, capacity, elementType);
}
@@ -811,6 +856,7 @@ public sealed class TypeChecker
VariableDeclarationSyntax varDeclStmt => CheckVariableDeclaration(varDeclStmt),
WhileSyntax whileStmt => CheckWhile(whileStmt),
DeferSyntax defer => new DeferNode(statement.Tokens, CheckStatement(defer.Statement)),
ForSyntax forSyntax => CheckFor(forSyntax),
_ => throw new ArgumentOutOfRangeException(nameof(statement))
};
}