def test_Function_definition_with_params_and_commands_gets_parsed(): assert ( parsed('{:(x,yy)print(3-4) a="x" print(a)}') == [ FunctionDefTree( [ SymbolTree("x"), SymbolTree("yy") ], [ FunctionCallTree( SymbolTree("print"), [ OperationTree( '-', NumberTree('3'), NumberTree('4') ) ] ), AssignmentTree(SymbolTree("a"), StringTree("x")), FunctionCallTree(SymbolTree("print"), [SymbolTree("a")]) ] ) ] )
def test_Multiple_function_calls_with_various_args_get_parsed(): assert ( parsed("print('a',3,4/12)(512)()") == [ FunctionCallTree( FunctionCallTree( FunctionCallTree( SymbolTree("print"), [ StringTree("a"), NumberTree("3"), OperationTree( "/", NumberTree("4"), NumberTree("12") ) ] ), [ NumberTree("512") ] ), [] ) ] )
def test_Multiple_function_calls_with_no_args_get_parsed(): assert ( parsed("print()()") == [ FunctionCallTree(FunctionCallTree(SymbolTree("print"), []), []) ] )
def times(env, reps, fn): # TODO: when we have "for" this should be written # in Cell, not Python. ret = None for i in range(int(reps.value)): ret = env.eval_expr(env, FunctionCallTree(fn, [])) return ret
def until_endofloop(env, fn): while True: y = env.eval_expr(env, FunctionCallTree(fn, [])) if y == env.get("endofloop"): break else: yield y
def test_Function_call_with_no_args_gets_parsed(): assert ( parsed("print()") == [ FunctionCallTree(SymbolTree("print"), []) ] )
def test_Multiple_commands_parse_into_multiple_expressions(): program = """ x=3 func={:(a)print(a)} func(x) """ assert ( parsed(program) == [ AssignmentTree(SymbolTree('x'), NumberTree('3')), AssignmentTree( SymbolTree('func'), FunctionDefTree( [SymbolTree('a')], [ FunctionCallTree( SymbolTree('print'), [SymbolTree('a')]) ] ) ), FunctionCallTree(SymbolTree('func'), [SymbolTree('x')]) ] )
def test_Function_call_with_various_args_gets_parsed(): assert ( parsed("print('a',3,4/12)") == [ FunctionCallTree( SymbolTree("print"), [ StringTree("a"), NumberTree("3"), OperationTree("/", NumberTree("4"), NumberTree("12")) ] ) ] )
def test_Spaces_are_allowed_where_unimportant(): assert ( parsed(''' {:( x, y ) x+y foo( 3 ) }( 3, 4 ) ''') == [ FunctionCallTree( FunctionDefTree( [ SymbolTree("x"), SymbolTree("y"), ], [ OperationTree( '+', SymbolTree("x"), SymbolTree("y"), ), FunctionCallTree( SymbolTree("foo"), [ NumberTree("3"), ] ), ] ), [ NumberTree("3"), NumberTree("4"), ] ) ] )
def for_(env, arr, fn): if type(arr) == ArrayValue: inp = arr.value elif type(arr) in (UserFunctionValue, NativeFunctionValue): inp = until_endofloop(env, arr) else: raise Exception( "Unexpected first argument to For: expected an array or a " + "function that eventually returns endofloop, but got: " + "%s." % arr ) return ArrayValue( [ env.eval_expr(env, FunctionCallTree(fn, [item])) for item in inp ] )
def dumb_if_equal(env, val1, val2, then_fn, else_fn): if val1 == val2: ret = then_fn else: ret = else_fn return eval_cell_list([FunctionCallTree(ret, [])], env)
def if_(env, condition, then_fn, else_fn): if env.eval_expr(env, condition).value != 0: return env.eval_expr(env, FunctionCallTree(then_fn, [])) else: return env.eval_expr(env, FunctionCallTree(else_fn, []))