<commit_before>import XCTest
import Song

class FunctionCallParserTests: XCTestCase {

    func test() {
        "1.inc".makes(.call("inc", [.int(1)]))
        "x.inc".makes(.call("inc", [.name("x")]))
        "1.inc()".makes(.call("inc", [.int(1)]))
        "1.inc.foo".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc.foo()".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc().foo".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc().foo()".makes(.call("foo", [.call("inc", [.int(1)])]))
        "foo().inc".makes(.call("inc", [.call("foo", [])]))
        "foo()().inc".makes(.call("inc", [.eval(.call("foo", []), [])]))
        "foo().bar()".makes(.call("bar", [.call("foo", [])]))
        "(5).foo.bar".makes(.call("bar", [.call("foo", [.int(5)])]))
        "(5.foo).bar".makes(.call("bar", [.call("foo", [.int(5)])]))
        "(5.foo)(4)".makes(.eval(.call("foo", [.int(5)]), [.int(4)]))
        "5.(foo).bar".makes(.call("bar", [.eval(.name("foo"), [.int(5)])]))
        "5.(foo.bar)".makes(.eval(.call("bar", [.name("foo")]), [.int(5)]))
        "(||5)()".makes(.eval(.lambda([], .int(5)), []))
        "(|x|x)(1)".makes(.eval(.lambda([.name("x")], .name("x")), [.int(1)]))
        "(|x|x)(1)(2)".makes(.eval(.eval(.lambda([.name("x")], .name("x")), [.int(1)]), [.int(2)]))
        "(|x|x)(1)(2).foo".makes(.call("foo", [.eval(.eval(.lambda([.name("x")], .name("x")), [.int(1)]), [.int(2)])]))
        "1.(|x|x)".makes(.eval(.lambda([.name("x")], .name("x")), [.int(1)]))
        "(foo)()".makes(.eval(.name("foo"), []))
        "(foo())()".makes(.eval(.call("foo", []), []))
        "foo()".makes(.call("foo", []))
        "foo(bar)".makes(.call("foo", [.name("bar")]))
        "foo(bar())".makes(.call("foo", [.call("bar", [])]))
        "foo(bar(baz()))".makes(.call("foo", [.call("bar", [.call("baz", [])])]))
        "foo(bar()())".makes(.call("foo", [.eval(.call("bar", []), [])]))
        "foo(bar(baz()())())".makes(.call("foo", [.eval(.call("bar", [.eval(.call("baz", []), [])]), [])]))
        "foo(bar(baz()())()).inc".ok()
//        "foo(|x|x)".makes(.call("foo", [.]))
        "foo((|x|x))".ok()
        "foo(|x|x,|y|y)".ok()
        "foo(|x|x.foo(bar()())(),1)".ok()

        "1.foo()".ok() //          # .call(foo, 1)
        "1.foo(2)(3)".ok() //      # .anon(.call(foo, 1, 2), 3)
        "1.foo(2)(3).bar".ok() //  # .call(bar, .anon(.call(foo, 1, 2), 3))
        "1.(foo)(2)(3)".ok() //    # .anon(.anon(.var(foo), 1), 2)
        "(1.foo)(2)".ok() //       # .anon(.call(foo, 1), 2)
        "1.foo()(2)".ok() //       # .anon(.call(foo, 1), 2)
        "1.(foo())(2)".ok() //     # .anon(.anon(.call(foo), 1) ,2)
        "1.foo(3)(4)".ok() //      # .anon(.call(foo, 1, 3), 4)
        "1.(foo(3))(2)".ok() //    # .anon(.anon(.call(foo, 3), 1), 2)
        "foo.bar.baz".ok() //      # .call(baz, .call(bar, .var(foo)))
        "foo(1).foo(2)(3).bar".ok() // # .call(bar, .anon(.call(foo, .call(foo, 1), 2), 3))
        "(foo).bar".ok() //        # .call(bar, .var(foo))
        "(foo(2)).bar".ok() //    # .call(bar, .call(foo, 2))
        "1.(foo.bar).bar".ok() //  # .call(bar, .anon(.call(bar, .var(foo)), 1))
        "(foo.bar).bar".ok() //    # .call(bar, .call(bar, .var(foo)))
        "foo(bar())".ok() //       # .call(foo, .call(bar))
        "foo(4.bar)".ok() //       # .call(foo, .call(bar, 4))
        "foo(4.bar())".ok() //     # .call(foo, .call(bar, 4))
        "foo().bar".ok() //        # .call(bar, .call(foo))
        "foo()().bar".ok() //      # .call(bar, .anon(.call(foo)))
        "foo.bar()()".ok() //      # .anon(.call(bar, .var(foo)))
        "foo(4.foo(bar(2))).(foo()().bar).bar(3)".ok() //  # .call(bar, ... , 3)
        "(|x|x)(1)".ok() //        # .anon(|x|x, 1)
        "(|x|x).foo(1)".ok() //    # .call(foo, |x|x, 1)
        "(x)(1)(2,3).bar".ok() //  # .call(bar, .anon(.anon(x, 1), 2, 3))
        "(|x|x)(1)(2,3).bar".ok() //    # .call(bar, .anon(.anon(|x|x, 1), 2, 3))
        "(|x|x)().bar".ok() //     # .call(bar, .anon(|x|x))
        "1.(|x|x)".ok() //         # .anon(|x|x, 1)
        "1.(|x|x)()".ok() //       # .anon(.anon(|x|x, 1))
        "foo().(|x|x)()".ok() //   # .anon(.anon(|x|x, .call(foo)))
        "foo.bar(|x|x).baz".ok() //# .call(baz, .call(bar, .var(foo), |x|x))
        "bar(|x|x)".ok() //        # .call(bar, |x|x)
        "bar(|x|foo(x))".ok() //   # .call(bar, |x|foo(x))
        "bar((|x|x))".ok() //      # .call(bar, |x|x)
        "x.foo(2)(3,4)(5).bar(6)(7)".ok() //
        "x.foo(2)(3).bar".ok() //  # .call(bar, .call(foo, 1, 2))
        "1.foo".ok() //            # .call(foo, 1)
        "lessthan(5)(4)".ok() //   # .anon(.call(lessThan, 5), 4)
        "(foo)()".ok() //
        "(1+2).foo".ok() //

        "4()".fails()
        "4.|x|x".fails()
        "(4)()".fails()
    }
}<commit_msg>More parser tests.<commit_after>import XCTest
import Song

class FunctionCallParserTests: XCTestCase {

    func test() {
        "1.inc".makes(.call("inc", [.int(1)]))
        "x.inc".makes(.call("inc", [.name("x")]))
        "1.inc()".makes(.call("inc", [.int(1)]))
        "1.inc.foo".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc.foo()".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc().foo".makes(.call("foo", [.call("inc", [.int(1)])]))
        "1.inc().foo()".makes(.call("foo", [.call("inc", [.int(1)])]))
        "foo().inc".makes(.call("inc", [.call("foo", [])]))
        "foo()().inc".makes(.call("inc", [.eval(.call("foo", []), [])]))
        "foo().bar()".makes(.call("bar", [.call("foo", [])]))
        "(5).foo.bar".makes(.call("bar", [.call("foo", [.int(5)])]))
        "(5.foo).bar".makes(.call("bar", [.call("foo", [.int(5)])]))
        "(5.foo)(4)".makes(.eval(.call("foo", [.int(5)]), [.int(4)]))
        "5.(foo).bar".makes(.call("bar", [.eval(.name("foo"), [.int(5)])]))
        "5.(foo.bar)".makes(.eval(.call("bar", [.name("foo")]), [.int(5)]))
        "(||5)()".makes(.eval(.lambda([], .int(5)), []))
        "(|x|x)(1)".makes(.eval(.lambda([.name("x")], .name("x")), [.int(1)]))
        "(|x|x)(1)(2)".makes(.eval(.eval(.lambda([.name("x")], .name("x")), [.int(1)]), [.int(2)]))
        "(|x|x)(1)(2).foo".makes(.call("foo", [.eval(.eval(.lambda([.name("x")], .name("x")), [.int(1)]), [.int(2)])]))
        "1.(|x|x)".makes(.eval(.lambda([.name("x")], .name("x")), [.int(1)]))
        "(foo)()".makes(.eval(.name("foo"), []))
        "(foo())()".makes(.eval(.call("foo", []), []))
        "foo()".makes(.call("foo", []))
        "foo(bar)".makes(.call("foo", [.name("bar")]))
        "foo(bar())".makes(.call("foo", [.call("bar", [])]))
        "foo(bar(baz()))".makes(.call("foo", [.call("bar", [.call("baz", [])])]))
        "foo(bar()())".makes(.call("foo", [.eval(.call("bar", []), [])]))
        "foo(bar(baz()())())".makes(.call("foo", [.eval(.call("bar", [.eval(.call("baz", []), [])]), [])]))
        "foo(bar(baz()())()).inc".ok()
        "foo(|x|x)".makes(.call("foo", [.lambda([.name("x")], .name("x"))]))
        "foo((|x|x))".makes(.call("foo", [.lambda([.name("x")], .name("x"))]))
        "foo(|x|x,|y|y)".makes(.call("foo", [.lambda([.name("x")], .name("x")), .lambda([.name("y")], .name("y"))]))
        "foo(|x|x.foo(bar()())(),1)".makes(.call("foo", [.eval(.lambda([.name("x")], .call("foo", [.name("x"), .eval(.call("bar", []), [])])), []), .int(1)]))
        "1.foo()".makes(.call("foo", [.int(1)]))
        "1.foo(2)(3)".makes(.eval(.call("foo", [.int(1), .int(2)]), [.int(3)]))
        "1.foo(2)(3).bar".makes(.call("bar", [.eval(.call("foo", [.int(1), .int(2)]), [.int(3)])]))
        "1.(foo)(2)(3)".makes(.eval(.eval(.eval(.name("foo"), [.int(1)]), [.int(2)]), [.int(3)]))
        "(1.foo)(2)".makes(.eval(.call("foo", [.int(1)]), [.int(2)]))
        "1.foo()(2)".makes(.eval(.call("foo", [.int(1)]), [.int(2)]))
        "1.(foo())(2)".makes(.eval(.eval(.call("foo", []), [.int(1)]), [.int(2)]))
        "1.foo(3)(4)".makes(.eval(.call("foo", [.int(1), .int(3)]), [.int(4)]))
        "1.(foo(3))(2)".makes(.eval(.eval(.call("foo", [.int(3)]), [.int(1)]), [.int(2)]))
        "foo.bar.baz".makes(.call("baz", [.call("bar", [.name("foo")])]))
        "foo(1).foo(2)(3).bar".ok() // # .call(bar, .eval(.call(foo, .call(foo, [.int(1), [.int(2), [.int(3))
        "(foo).bar".ok() //        # .call(bar, .var(foo))
        "(foo(2)).bar".ok() //    # .call(bar, .call(foo, [.int(2))
        "1.(foo.bar).bar".ok() //  # .call(bar, .eval(.call(bar, .var(foo)), [.int(1))
        "(foo.bar).bar".ok() //    # .call(bar, .call(bar, .var(foo)))
        "foo(bar())".ok() //       # .call(foo, .call(bar))
        "foo(4.bar)".ok() //       # .call(foo, .call(bar, [.int(4))
        "foo(4.bar())".ok() //     # .call(foo, .call(bar, [.int(4))
        "foo().bar".ok() //        # .call(bar, .call(foo))
        "foo()().bar".ok() //      # .call(bar, .eval(.call(foo)))
        "foo.bar()()".ok() //      # .eval(.call(bar, .var(foo)))
        "foo(4.foo(bar(2))).(foo()().bar).bar(3)".ok() //  # .call(bar, ... , [.int(3)
        "(|x|x)(1)".ok() //        # .eval(|x|x, 1)
        "(|x|x).foo(1)".ok() //    # .call(foo, |x|x, 1)
        "(x)(1)(2,3).bar".ok() //  # .call(bar, .eval(.eval(x, [.int(1), [.int(2, [.int(3))
        "(|x|x)(1)(2,3).bar".ok() //    # .call(bar, .eval(.eval(|x|x, [.int(1), [.int(2, [.int(3))
        "(|x|x)().bar".ok() //     # .call(bar, .eval(|x|x))
        "1.(|x|x)".ok() //         # .eval(|x|x, 1)
        "1.(|x|x)()".ok() //       # .eval(.eval(|x|x, [.int(1))
        "foo().(|x|x)()".ok() //   # .eval(.eval(|x|x, .call(foo)))
        "foo.bar(|x|x).baz".ok() //# .call(baz, .call(bar, .var(foo), |x|x))
        "bar(|x|x)".ok() //        # .call(bar, |x|x)
        "bar(|x|foo(x))".ok() //   # .call(bar, |x|foo(x))
        "bar((|x|x))".ok() //      # .call(bar, |x|x)
        "x.foo(2)(3,4)(5).bar(6)(7)".ok() //
        "x.foo(2)(3).bar".ok() //  # .call(bar, .call(foo, [.int(1)], [.int(2)]))
        "1.foo".ok() //            # .call(foo, [.int(1)])
        "lessthan(5)(4)".ok() //   # .eval(.call(lessThan, [.int(5)]), [.int(4)])
        "(foo)()".ok() //
        "(1+2).foo".ok() //

        "4()".fails()
        "4.|x|x".fails()
        "(4)()".fails()
    }
}
{'fraction_non_alphanumeric': 0.388937836514929, 'fraction_numerical': 0.027802251590797845, 'mean_word_length': 2.3738441215323647, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, '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': '6955309', 'n_tokens_mistral': 4712, 'n_tokens_neox': 4421, 'n_words': 482}