Ast ternary expr replaced by cond expr

This commit is contained in:
Michael Schimmel
2025-12-07 12:06:29 +01:00
parent 91c4d57aaf
commit 1d13d0cdaa
15 changed files with 449 additions and 180 deletions
+57 -19
View File
@@ -31,7 +31,8 @@ type
function JsonToIdentifierNode(const AObj: TJSONObject): IIdentifierNode;
function JsonToKeywordNode(const AObj: TJSONObject): IKeywordNode;
function JsonToIfExprNode(const AObj: TJSONObject): IIfExpressionNode;
function JsonToTernaryExprNode(const AObj: TJSONObject): ITernaryExpressionNode;
function JsonToCondExprNode(const AObj: TJSONObject): ICondExpressionNode;
function JsonToTernaryExprNode(const AObj: TJSONObject): IAstNode; // Backward Compatibility
function JsonToLambdaExprNode(const AObj: TJSONObject): ILambdaExpressionNode;
function JsonToMacroDefNode(const AObj: TJSONObject): IMacroDefinitionNode;
function JsonToQuasiquoteNode(const AObj: TJSONObject): IQuasiquoteNode;
@@ -44,7 +45,7 @@ type
function JsonToVarDeclNode(const AObj: TJSONObject): IVariableDeclarationNode;
function JsonToAssignmentNode(const AObj: TJSONObject): IAssignmentNode;
function JsonToIndexerNode(const AObj: TJSONObject): IIndexerNode;
function JsonToMemberAccessNode(const AObj: TJSONObject): IMemberAccessNode; // <--- KORRIGIERT
function JsonToMemberAccessNode(const AObj: TJSONObject): IMemberAccessNode;
function JsonToRecordLiteralNode(const AObj: TJSONObject): IRecordLiteralNode;
function JsonToCreateSeriesNode(const AObj: TJSONObject): ICreateSeriesNode;
function JsonToAddSeriesItemNode(const AObj: TJSONObject): IAddSeriesItemNode;
@@ -57,7 +58,7 @@ type
function VisitIdentifier(const Node: IIdentifierNode): TJSONObject; override;
function VisitKeyword(const Node: IKeywordNode): TJSONObject; override;
// List Visitors (stubbed mostly, as parents handle array generation for JSON structure)
// List Visitors
function VisitParameterList(const Node: IParameterList): TJSONObject; override;
function VisitArgumentList(const Node: IArgumentList): TJSONObject; override;
function VisitExpressionList(const Node: IExpressionList): TJSONObject; override;
@@ -65,7 +66,7 @@ type
function VisitRecordField(const Node: IRecordFieldNode): TJSONObject; override;
function VisitIfExpression(const Node: IIfExpressionNode): TJSONObject; override;
function VisitTernaryExpression(const Node: ITernaryExpressionNode): TJSONObject; override;
function VisitCondExpression(const Node: ICondExpressionNode): TJSONObject; override;
function VisitLambdaExpression(const Node: ILambdaExpressionNode): TJSONObject; override;
function VisitMacroDefinition(const Node: IMacroDefinitionNode): TJSONObject; override;
function VisitQuasiquote(const Node: IQuasiquoteNode): TJSONObject; override;
@@ -186,19 +187,32 @@ begin
Result.AddPair('ElseBranch', TJSONNull.Create);
end;
function TJsonAstConverter.VisitTernaryExpression(const Node: ITernaryExpressionNode): TJSONObject;
function TJsonAstConverter.VisitCondExpression(const Node: ICondExpressionNode): TJSONObject;
var
condObj, thenObj, elseObj: TJSONObject;
pairsArray: TJSONArray;
pairObj: TJSONObject;
elseObj: TJSONObject;
i: Integer;
begin
condObj := Accept(Node.Condition);
thenObj := Accept(Node.ThenBranch);
elseObj := Accept(Node.ElseBranch);
pairsArray := TJSONArray.Create;
for i := 0 to High(Node.Pairs) do
begin
pairObj := TJSONObject.Create;
pairObj.AddPair('Condition', Accept(Node.Pairs[i].Condition));
pairObj.AddPair('Branch', Accept(Node.Pairs[i].Branch));
pairsArray.Add(pairObj);
end;
elseObj := Accept(Node.ElseBranch); // Accept handles nil
Result := TJSONObject.Create;
Result.AddPair('NodeType', TJSONString.Create('TernaryExpr'));
Result.AddPair('Condition', condObj);
Result.AddPair('ThenBranch', thenObj);
Result.AddPair('ElseBranch', elseObj);
Result.AddPair('NodeType', TJSONString.Create('CondExpr'));
Result.AddPair('Pairs', pairsArray);
if Assigned(elseObj) then
Result.AddPair('ElseBranch', elseObj)
else
Result.AddPair('ElseBranch', TJSONNull.Create);
end;
function TJsonAstConverter.VisitLambdaExpression(const Node: ILambdaExpressionNode): TJSONObject;
@@ -451,10 +465,6 @@ begin
end;
// --- List Visitors (Placeholder return) ---
// Since we iterate manually in parent nodes to form JSON Arrays, these are technically not used
// by the current logic, but required by the interface.
// Note: If we wanted strict visitor compliance, VisitFunctionCall would call Accept(List),
// which would return TJSONObject wrapping the array. We skip that level of nesting here.
function TJsonAstConverter.VisitParameterList(const Node: IParameterList): TJSONObject;
begin
@@ -544,13 +554,39 @@ begin
Result := TAst.IfExpr(condNode, thenNode, elseNode);
end;
function TJsonAstConverter.JsonToTernaryExprNode(const AObj: TJSONObject): ITernaryExpressionNode;
function TJsonAstConverter.JsonToCondExprNode(const AObj: TJSONObject): ICondExpressionNode;
var
pairsArray: TJSONArray;
pairs: TArray<TCondPair>;
elseNode: IAstNode;
i: Integer;
pairObj: TJSONObject;
begin
pairsArray := AObj.GetValue<TJSONArray>('Pairs');
SetLength(pairs, pairsArray.Count);
for i := 0 to pairsArray.Count - 1 do
begin
pairObj := pairsArray.Items[i] as TJSONObject;
pairs[i] := TCondPair.Create(JsonToNode(pairObj.GetValue('Condition')), JsonToNode(pairObj.GetValue('Branch')));
end;
if not (AObj.GetValue('ElseBranch') is TJSONNull) then
elseNode := JsonToNode(AObj.GetValue('ElseBranch'))
else
elseNode := nil;
Result := TAst.CondExpr(pairs, elseNode);
end;
function TJsonAstConverter.JsonToTernaryExprNode(const AObj: TJSONObject): IAstNode;
var
condNode, thenNode, elseNode: IAstNode;
begin
condNode := JsonToNode(AObj.GetValue('Condition'));
thenNode := JsonToNode(AObj.GetValue('ThenBranch'));
elseNode := JsonToNode(AObj.GetValue('ElseBranch'));
// Map to CondExpr using the helper in TAst
Result := TAst.TernaryExpr(condNode, thenNode, elseNode);
end;
@@ -775,8 +811,10 @@ begin
Result := JsonToKeywordNode(obj)
else if nodeType = 'IfExpr' then
Result := JsonToIfExprNode(obj)
else if nodeType = 'CondExpr' then
Result := JsonToCondExprNode(obj)
else if nodeType = 'TernaryExpr' then
Result := JsonToTernaryExprNode(obj)
Result := JsonToTernaryExprNode(obj) // Backward Compatibility
else if nodeType = 'LambdaExpr' then
Result := JsonToLambdaExprNode(obj)
else if nodeType = 'MacroDef' then