<commit_before>package haxpression;

import utest.Assert;
using haxpression.AssertExpressionString;

class TestParser {
  public function new() {
  }

  public function testSpaces() {
    "2+3".evaluatesToInt(5);
    "2+3".evaluatesToInt(5);
    "2+ 3".evaluatesToInt(5);
    "2 +3".evaluatesToInt(5);
    " 2+3".evaluatesToInt(5);
    "2+3 ".evaluatesToInt(5);
    "2 + 3".evaluatesToInt(5);
    " 2 + 3".evaluatesToInt(5);
    " 2 + 3 ".evaluatesToInt(5);
    " 2 + 3 ".evaluatesToInt(5);
    "2  +  3".evaluatesToInt(5);
    " 2  +  3 ".evaluatesToInt(5);
  }

  public function testLogical() {
    "true || false".evaluatesToTrue();
    "false || true".evaluatesToTrue();
    "true || true".evaluatesToTrue();
    "false || false".evaluatesToFalse();
    "true && false".evaluatesToFalse();
    "false && true".evaluatesToFalse();
    "true && true".evaluatesToTrue();
    "false && false".evaluatesToFalse();

    // Note: && has higher precedence than ||
    "true && true || true".evaluatesToTrue();
    "false && true || true".evaluatesToTrue();
    "true && false || true".evaluatesToTrue();
    "false && false || true".evaluatesToTrue();

    "true && true || false".evaluatesToTrue();
    "false && true || false".evaluatesToFalse();
    "true && false || false".evaluatesToFalse();
    "false && false || false".evaluatesToFalse();

    "true || true && true".evaluatesToTrue();
    "false || true && true".evaluatesToTrue();
    "true || false && true".evaluatesToTrue();
    "false || false && true".evaluatesToFalse();

    "true || true && false".evaluatesToTrue();
    "false || true && false".evaluatesToFalse();
    "true || false && false".evaluatesToTrue();
    "false || false && false".evaluatesToFalse();
  }

  public function testAddition() {
    "2 + 3".evaluatesToInt(2 + 3);
    "3 + 4.7".evaluatesToFloat(3 + 4.7);
    "2 + 3 + 4.7".evaluatesToFloat(2 + 3 + 4.7);
  }

  public function testSubtraction() {
    "2 - 3".evaluatesToInt(2 - 3);
    "3 - 4.7".evaluatesToFloat(3 - 4.7);
    "2 - 3 - 4.7".evaluatesToFloat(2 - 3 - 4.7);
  }

  public function testAdditionAndSubtraction() {
    "2 - 3 + 4.7".evaluatesToFloat(2 - 3 + 4.7);
    "2 + 3 - 4.7".evaluatesToFloat(2 + 3 - 4.7);
  }

  public function testMultiplication() {
    '2 * 3'.evaluatesToInt(2 * 3);
    '2 * 4.7'.evaluatesToFloat(2 * 4.7);
    '2 * 4.7 * 3'.evaluatesToFloat(2 * 4.7 * 3);
  }

  public function testDivision() {
    '2 / 3'.evaluatesToFloat(2 / 3);
    '2 / 4.7'.evaluatesToFloat(2 / 4.7);
    '2 / 4.7 / 3'.evaluatesToFloat(2 / 4.7 / 3);
  }

  public function testMultiplicationAndDivison() {
    '2 * 4.7 / 3'.evaluatesToFloat(2 * 4.7 / 3);
    '2 / 4.7 * 3'.evaluatesToFloat(2 / 4.7 * 3);
  }

  public function testWithVariables() {
    var result1 : Float = ('PI * pow(r, 2)' : Expression).evaluate([
      "PI" => Math.PI,
      "r" => 10
    ]);
    Assert.same(Math.PI * Math.pow(10, 2), result1);
  }

  public function testWithExpressionSubstitutions() {
    var mappings : Map<String, Expression> = [
      "MAP_VALUE_1" => "2 * SOURCE_1 + 0.5 * SOURCE_2",
      "MAP_VALUE_2" => "4 * SOURCE_1 + 10 * SOURCE_3",
      "MAP_VALUE_3" => "2 * SOURCE_1 + 0.3 * MAP_VALUE_2"
    ];

    var hasMapVariables = true;
    while (hasMapVariables) {
    }
    for (key in mappings.keys()) {
    }

  }

  public function testToString(){
    '1 + 2'.toStringSameAs('(1 + 2)');
    '1 + 2 + 3'.toStringSameAs('((1 + 2) + 3)');
    '1 + 2 + 3 + 4'.toStringSameAs('(((1 + 2) + 3) + 4)');
    '1 + 2 * 3 + 4'.toStringSameAs('((1 + (2 * 3)) + 4)');
    '1 * 2 + 3 * 4'.toStringSameAs('((1 * 2) + (3 * 4))');
    '1 * PI + MY_VAR * 4'.toStringSameAs('((1 * PI) + (MY_VAR * 4))');
  }

  public function testToObject() {
    '1 + 2'.toObjectSameAs({
      type: "Binary",
      operator: "+",
      left: {
        type: "Literal",
        value: 1
      },
      right: {
        type: "Literal",
        value: 2
      }<commit_msg>Remove unfinished loop in tests<commit_after>package haxpression;

import utest.Assert;
using haxpression.AssertExpressionString;

class TestParser {
  public function new() {
  }

  public function testSpaces() {
    "2+3".evaluatesToInt(5);
    "2+3".evaluatesToInt(5);
    "2+ 3".evaluatesToInt(5);
    "2 +3".evaluatesToInt(5);
    " 2+3".evaluatesToInt(5);
    "2+3 ".evaluatesToInt(5);
    "2 + 3".evaluatesToInt(5);
    " 2 + 3".evaluatesToInt(5);
    " 2 + 3 ".evaluatesToInt(5);
    " 2 + 3 ".evaluatesToInt(5);
    "2  +  3".evaluatesToInt(5);
    " 2  +  3 ".evaluatesToInt(5);
  }

  public function testLogical() {
    "true || false".evaluatesToTrue();
    "false || true".evaluatesToTrue();
    "true || true".evaluatesToTrue();
    "false || false".evaluatesToFalse();
    "true && false".evaluatesToFalse();
    "false && true".evaluatesToFalse();
    "true && true".evaluatesToTrue();
    "false && false".evaluatesToFalse();

    // Note: && has higher precedence than ||
    "true && true || true".evaluatesToTrue();
    "false && true || true".evaluatesToTrue();
    "true && false || true".evaluatesToTrue();
    "false && false || true".evaluatesToTrue();

    "true && true || false".evaluatesToTrue();
    "false && true || false".evaluatesToFalse();
    "true && false || false".evaluatesToFalse();
    "false && false || false".evaluatesToFalse();

    "true || true && true".evaluatesToTrue();
    "false || true && true".evaluatesToTrue();
    "true || false && true".evaluatesToTrue();
    "false || false && true".evaluatesToFalse();

    "true || true && false".evaluatesToTrue();
    "false || true && false".evaluatesToFalse();
    "true || false && false".evaluatesToTrue();
    "false || false && false".evaluatesToFalse();
  }

  public function testAddition() {
    "2 + 3".evaluatesToInt(2 + 3);
    "3 + 4.7".evaluatesToFloat(3 + 4.7);
    "2 + 3 + 4.7".evaluatesToFloat(2 + 3 + 4.7);
  }

  public function testSubtraction() {
    "2 - 3".evaluatesToInt(2 - 3);
    "3 - 4.7".evaluatesToFloat(3 - 4.7);
    "2 - 3 - 4.7".evaluatesToFloat(2 - 3 - 4.7);
  }

  public function testAdditionAndSubtraction() {
    "2 - 3 + 4.7".evaluatesToFloat(2 - 3 + 4.7);
    "2 + 3 - 4.7".evaluatesToFloat(2 + 3 - 4.7);
  }

  public function testMultiplication() {
    '2 * 3'.evaluatesToInt(2 * 3);
    '2 * 4.7'.evaluatesToFloat(2 * 4.7);
    '2 * 4.7 * 3'.evaluatesToFloat(2 * 4.7 * 3);
  }

  public function testDivision() {
    '2 / 3'.evaluatesToFloat(2 / 3);
    '2 / 4.7'.evaluatesToFloat(2 / 4.7);
    '2 / 4.7 / 3'.evaluatesToFloat(2 / 4.7 / 3);
  }

  public function testMultiplicationAndDivison() {
    '2 * 4.7 / 3'.evaluatesToFloat(2 * 4.7 / 3);
    '2 / 4.7 * 3'.evaluatesToFloat(2 / 4.7 * 3);
  }

  public function testWithVariables() {
    var result1 : Float = ('PI * pow(r, 2)' : Expression).evaluate([
      "PI" => Math.PI,
      "r" => 10
    ]);
    Assert.same(Math.PI * Math.pow(10, 2), result1);
  }

  public function testWithExpressionSubstitutions() {
    var mappings : Map<String, Expression> = [
      "MAP_VALUE_1" => "2 * SOURCE_1 + 0.5 * SOURCE_2",
      "MAP_VALUE_2" => "4 * SOURCE_1 + 10 * SOURCE_3",
      "MAP_VALUE_3" => "2 * SOURCE_1 + 0.3 * MAP_VALUE_2"
    ];
    //var hasMapVariables = true;
    //while (hasMapVariables) {
    //}
    //for (key in mappings.keys()) {
    //}
  }

  public function testToString(){
    '1 + 2'.toStringSameAs('(1 + 2)');
    '1 + 2 + 3'.toStringSameAs('((1 + 2) + 3)');
    '1 + 2 + 3 + 4'.toStringSameAs('(((1 + 2) + 3) + 4)');
    '1 + 2 * 3 + 4'.toStringSameAs('((1 + (2 * 3)) + 4)');
    '1 * 2 + 3 * 4'.toStringSameAs('((1 * 2) + (3 * 4))');
    '1 * PI + MY_VAR * 4'.toStringSameAs('((1 * PI) + (MY_VAR * 4))');
  }

  public function testToObject() {
    '1 + 2'.toObjectSameAs({
      type: "Binary",
      operator: "+",
      left: {
        type: "Literal",
        value: 1
      },
      right: {
        type: "Literal",
        value: 2
      }
{'fraction_non_alphanumeric': 0.19671302149178255, 'fraction_numerical': 0.05259165613147914, 'mean_word_length': 2.7088607594936707, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 15, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2989685', 'n_tokens_mistral': 3137, 'n_tokens_neox': 2896, 'n_words': 600}