mirror of
https://github.com/Laupetin/OpenAssetTools.git
synced 2025-04-21 00:25:44 +00:00
ZoneCodeGenerator: When parsing Evaluation nest operations so the operator precendence is evaluated as specified
This commit is contained in:
parent
0a8d5246b2
commit
6c1404116c
@ -16,6 +16,7 @@ namespace ZoneCodeGenerator.Parsing.CommandFile.Tests
|
|||||||
|
|
||||||
// Evaluation Sub-Tags
|
// Evaluation Sub-Tags
|
||||||
private const string TagEvaluationParenthesis = "evaluationParenthesis";
|
private const string TagEvaluationParenthesis = "evaluationParenthesis";
|
||||||
|
private const string TagEvaluationParenthesisEnd = "evaluationParenthesisEnd";
|
||||||
private const string TagEvaluationNot = "evaluationNot";
|
private const string TagEvaluationNot = "evaluationNot";
|
||||||
private const string TagEvaluationOperation = "evaluationOperation";
|
private const string TagEvaluationOperation = "evaluationOperation";
|
||||||
|
|
||||||
@ -53,7 +54,7 @@ namespace ZoneCodeGenerator.Parsing.CommandFile.Tests
|
|||||||
new MatcherGroupOptional(new MatcherLiteral("!").WithTag(TagEvaluationNot)),
|
new MatcherGroupOptional(new MatcherLiteral("!").WithTag(TagEvaluationNot)),
|
||||||
new MatcherLiteral("("),
|
new MatcherLiteral("("),
|
||||||
new MatcherWithTag(TagEvaluation),
|
new MatcherWithTag(TagEvaluation),
|
||||||
new MatcherLiteral(")")
|
new MatcherLiteral(")").WithTag(TagEvaluationParenthesisEnd)
|
||||||
).WithTag(TagEvaluationParenthesis),
|
).WithTag(TagEvaluationParenthesis),
|
||||||
new MatcherWithTag(TagOperand)
|
new MatcherWithTag(TagOperand)
|
||||||
),
|
),
|
||||||
@ -108,16 +109,29 @@ namespace ZoneCodeGenerator.Parsing.CommandFile.Tests
|
|||||||
|
|
||||||
private IEvaluation ProcessEvaluationInParenthesis(ICommandParserState state)
|
private IEvaluation ProcessEvaluationInParenthesis(ICommandParserState state)
|
||||||
{
|
{
|
||||||
|
var isNegated = false;
|
||||||
if (NextTag().Equals(TagEvaluationNot))
|
if (NextTag().Equals(TagEvaluationNot))
|
||||||
{
|
{
|
||||||
NextTag();
|
NextTag();
|
||||||
return new Operation(ProcessEvaluation(state), new OperandStatic(0), OperationType.OperationEquals);
|
isNegated = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return ProcessEvaluation(state);
|
var processedEvaluation = ProcessEvaluation(state);
|
||||||
|
|
||||||
|
if (NextTag() != TagEvaluationParenthesisEnd)
|
||||||
|
throw new Exception("Expected parenthesis end tag @ EvaluationInParenthesis");
|
||||||
|
|
||||||
|
return !isNegated
|
||||||
|
? processedEvaluation
|
||||||
|
: new Operation(processedEvaluation, new OperandStatic(0), OperationType.OperationEquals);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected IEvaluation ProcessEvaluation(ICommandParserState state)
|
protected IEvaluation ProcessEvaluation(ICommandParserState state)
|
||||||
|
{
|
||||||
|
var operands = new List<IEvaluation>();
|
||||||
|
var operators = new List<OperationType>();
|
||||||
|
|
||||||
|
while (true)
|
||||||
{
|
{
|
||||||
IEvaluation firstStatementPart;
|
IEvaluation firstStatementPart;
|
||||||
switch (NextTag())
|
switch (NextTag())
|
||||||
@ -133,6 +147,7 @@ namespace ZoneCodeGenerator.Parsing.CommandFile.Tests
|
|||||||
default:
|
default:
|
||||||
throw new Exception("Invalid followup tag @ Evaluation");
|
throw new Exception("Invalid followup tag @ Evaluation");
|
||||||
}
|
}
|
||||||
|
operands.Add(firstStatementPart);
|
||||||
|
|
||||||
if (PeekTag() == TagEvaluationOperation)
|
if (PeekTag() == TagEvaluationOperation)
|
||||||
{
|
{
|
||||||
@ -141,17 +156,31 @@ namespace ZoneCodeGenerator.Parsing.CommandFile.Tests
|
|||||||
if (NextTag() != TagOperationType)
|
if (NextTag() != TagOperationType)
|
||||||
throw new Exception("Expected operationType tag @ Evaluation");
|
throw new Exception("Expected operationType tag @ Evaluation");
|
||||||
|
|
||||||
var type = ProcessOperationType(state);
|
operators.Add(ProcessOperationType(state));
|
||||||
|
|
||||||
if (NextTag() != TagEvaluation)
|
if (NextTag() != TagEvaluation)
|
||||||
throw new Exception("Expected EvaluationTag @ Evaluation");
|
throw new Exception("Expected EvaluationTag @ Evaluation");
|
||||||
|
}
|
||||||
var secondStatementPart = ProcessEvaluation(state);
|
else
|
||||||
|
{
|
||||||
return new Operation(firstStatementPart, secondStatementPart, type);
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return firstStatementPart;
|
while (operators.Any())
|
||||||
|
{
|
||||||
|
var nextOperator = operators
|
||||||
|
.OrderBy(type => type.Precedence)
|
||||||
|
.First();
|
||||||
|
var operatorIndex = operators.IndexOf(nextOperator);
|
||||||
|
|
||||||
|
var operation = new Operation(operands[operatorIndex], operands[operatorIndex + 1], nextOperator);
|
||||||
|
operands.RemoveRange(operatorIndex, 2);
|
||||||
|
operands.Insert(operatorIndex, operation);
|
||||||
|
operators.RemoveAt(operatorIndex);
|
||||||
|
}
|
||||||
|
|
||||||
|
return operands[0];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
Loading…
x
Reference in New Issue
Block a user