public void ZeroReturnsFalse() { var parsed = MoLangParser.Parse("return 0 ?? 'test'"); var result = _runtime.Execute(parsed); Assert.AreEqual(result.AsString(), "test"); }
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) { JToken token = JToken.Load(reader); if (token.Type == JTokenType.String) { string molang = token.Value <string>(); return(MoLangParser.Parse(molang)); } else if (token.Type == JTokenType.Integer) { return(new NumberExpression(token.Value <double>())); } else if (token.Type == JTokenType.Float) { return(new NumberExpression(token.Value <double>())); } else if (token.Type == JTokenType.Boolean) { return(new BooleanExpression(token.Value <bool>())); } return(existingValue); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { IExpression expr = parser.ParseExpression(); var result = parser.ConsumeToken(TokenType.BracketRight); return(expr); }
public void ZeroVariableReturnsFalse() { _runtime.Environment.SetValue(new MoPath("variable.lastNumber"), new DoubleValue(0)); var parsed = MoLangParser.Parse("return variable.lastNumber ?? 'test'"); var result = _runtime.Execute(parsed); Assert.AreEqual(result.AsString(), "test"); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token, IExpression leftExpr) { IExpression index = parser.ParseExpression(Precedence); parser.ConsumeToken(TokenType.ArrayRight); return(new ArrayAccessExpression(leftExpr, index)); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { if (double.TryParse(token.Text, NumberStyle, Culture, out var result)) { return(new NumberExpression(result)); } throw new MoLangParserException($"Could not parse \'{token.Text.ToString()}\' as a double"); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { if (!parser.TryParseArgs(out var expressions) || expressions.Length != 3) { throw new MoLangParserException($"ForEach: Expected 3 argument, {(expressions?.Length ?? 0)} argument given"); } return(new ForEachExpression(expressions[0], expressions[1], expressions[2])); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { var path = parser.FixNameShortcut(new MoPath(token.Text)); if (parser.TryParseArgs(out var expressions)) { return(new FuncCallExpression(path, expressions)); } return(new NameExpression(path)); }
public void ArithmeticsDivision() { const double a = 1200; const double b = 800; const double expectedResult = a / b; var expression = MoLangParser.Parse("v.a / v.b"); var runtime = Setup(a, b); var result = runtime.Execute(expression); Assert.AreEqual(expectedResult, result.AsDouble()); }
public void PropertyWrite() { var expression = MoLangParser.Parse("query.life_time = 5"); MoLangRuntime runtime = new MoLangRuntime(); var testStruct = new TestClass(Environment.TickCount); runtime.Environment.Structs.TryAdd( "query", new InteropStruct(testStruct)); runtime.Execute(expression); Assert.AreEqual(5d, testStruct.Lifetime); }
public void PropertyRead() { var expression = MoLangParser.Parse("query.life_time"); var expected = Environment.TickCount * 3.5d; MoLangRuntime runtime = new MoLangRuntime(); runtime.Environment.Structs.TryAdd( "query", new InteropStruct(new TestClass(expected))); var result = runtime.Execute(expression); Assert.AreEqual(expected, result.AsDouble()); }
public void MathFunctions() { MoLangParser parser = new MoLangParser(new TokenIterator("math.floor(10.1 + 20.1)")); parser.ExpressionTraverser.Visitors.Add(new MathOptimizationVisitor()); var expr = parser.Parse(); Assert.IsInstanceOfType(expr, typeof(NumberExpression)); MoLangRuntime runtime = new MoLangRuntime(); var result = runtime.Execute(expr); Assert.AreEqual(30, result.AsDouble()); }
public void Constants() { MoLangParser parser = new MoLangParser(new TokenIterator("7 + 2 * (6 + 3) / 3 - 7")); parser.ExpressionTraverser.Visitors.Add(new MathOptimizationVisitor()); var expr = parser.Parse(); Assert.IsInstanceOfType(expr, typeof(NumberExpression)); MoLangRuntime runtime = new MoLangRuntime(); var result = runtime.Execute(expr); Assert.AreEqual(6, result.AsDouble()); }
public void OrderOfOperations() { var runtime = Setup(10, 20); var expr = MoLangParser.Parse("v.b + (7 + 2 * (6 + 3) / 3 - 7) + v.a"); var result = runtime.Execute(expr); Assert.AreEqual(36, result.AsDouble()); result = runtime.Execute(MoLangParser.Parse("10 * 2 - (7 + 9)")); Assert.AreEqual(4, result.AsDouble()); result = runtime.Execute(MoLangParser.Parse("12 + 2 * 44")); Assert.AreEqual(100, result.AsDouble()); }
public void EqualityOperatorTest() { var parsed = MoLangParser.Parse(@" t.a = 10; loop(10, { t.a = t.a - 1; t.a == 5 ? break : continue; }); return t.a; "); Assert.IsNotNull(parsed); var result = _runtime.Execute(parsed); Assert.AreEqual(5, result.AsDouble()); }
public void BiggerOrEqualTest() { var parsed = MoLangParser.Parse(@" t.a = 1; loop(10, { t.a = t.a + 1; t.a >= 5 ? break : continue; }); return t.a; "); Assert.IsNotNull(parsed); var result = _runtime.Execute(parsed); Assert.AreEqual(5, result.AsDouble()); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token, IExpression leftExpr) { if (parser.MatchToken(TokenType.Colon)) { return(new TernaryExpression(leftExpr, null, parser.ParseExpression(Precedence))); } else { IExpression thenExpr = parser.ParseExpression(Precedence); if (!parser.MatchToken(TokenType.Colon)) { return(new TernaryExpression(leftExpr, thenExpr, null)); } else { return(new TernaryExpression(leftExpr, thenExpr, parser.ParseExpression(Precedence))); } } }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { List <IExpression> exprs = new List <IExpression>(); if (!parser.MatchToken(TokenType.CurlyBracketRight)) { do { if (parser.MatchToken(TokenType.CurlyBracketRight, false)) { break; } exprs.Add(parser.ParseExpression(Precedence.Scope)); } while (parser.MatchToken(TokenType.Semicolon)); parser.ConsumeToken(TokenType.CurlyBracketRight); } return(new StatementExpression(exprs.ToArray())); }
public void ScriptRun() { _sw.Start(); var parsed = MoLangParser.Parse(@" t.a = 213 + 2 / 0.5 + 5 + 2 * 3; query.debug_output(1 + 2 * 3); array.test.0 = 100; array.test[1] = 200; array.test[2] = 10.5; query.debug_output(array.test[1]); t.b = 3; loop(10, { array.test[t.b] = array.test[t.b - 1] + 2; t.b = t.b + 1; }); for_each(v.r, array.test, { t.a = t.a + v.r; query.debug_output('hello1', t.a, v.r); }); t.b = 0; loop(100, { t.b = t.b + 1; t.a = t.a + math.cos((Math.PI / 180.0f) * 270) + t.b; query.debug_output(array.test[t.b]); query.debug_output('hello', 'test', t.a, array.test[2], t.b); }); query.debug_output(query.life_time()); return t.a; "); _sw.Stop(); var timeElapsedOnParsing = _sw.Elapsed; Assert.IsNotNull(parsed); Console.WriteLine($"Parser completed in {timeElapsedOnParsing.TotalMilliseconds}ms"); const int runs = 1000; const int warmupRuns = 10; TimeSpan totalElapsed = TimeSpan.Zero; TimeSpan max = TimeSpan.Zero; TimeSpan min = TimeSpan.MaxValue; for (int i = 0; i < runs + warmupRuns; i++) { _sw.Restart(); _runtime.Execute(parsed); _sw.Stop(); if (i >= warmupRuns) { totalElapsed += _sw.Elapsed; if (_sw.Elapsed < min) { min = _sw.Elapsed; } if (_sw.Elapsed > max) { max = _sw.Elapsed; } } } Console.WriteLine($"Executed {runs} runs. Total={totalElapsed.TotalMilliseconds}ms Avg={totalElapsed.TotalMilliseconds / runs}ms Max={max.TotalMilliseconds}ms Min={min.TotalMilliseconds}ms"); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new ContinueExpression()); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token, IExpression leftExpr) { return(new AssignExpression(leftExpr, parser.ParseExpression(Precedence))); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new ReturnExpression(parser.ParseExpression())); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token, IExpression leftExpr) { IExpression rightExpr = parser.ParseExpression(Precedence); if (token.Type.Equals(TokenType.Arrow)) { return(new ArrowExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.And)) { return(new BooleanAndExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Or)) { return(new BooleanOrExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Coalesce)) { return(new CoalesceExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Slash)) { return(new DivideExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.EqualsEquals)) { return(new EqualExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Greater)) { return(new GreaterExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.GreaterOrEquals)) { return(new GreaterOrEqualExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Minus)) { return(new MinusExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.NotEquals)) { return(new NotEqualExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Plus)) { return(new PlusExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Asterisk)) { return(new PowExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.Smaller)) { return(new SmallerExpression(leftExpr, rightExpr)); } if (token.Type.Equals(TokenType.SmallerOrEquals)) { return(new SmallerOrEqualExpression(leftExpr, rightExpr)); } return(null); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new BreakExpression()); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new UnaryMinusExpression(parser.ParseExpression(Precedence.Prefix))); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new BooleanNotExpression(parser.ParseExpression(Precedence.Prefix))); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new StringExpression(token.Text)); }
/// <inheritdoc /> public override IExpression Parse(MoLangParser parser, Token token) { return(new BooleanExpression(bool.Parse(token.Text))); }