Added lambdas. Rolled back print bootstrapping for test. Need to figure out right story for polymorphic print at some point.

This commit is contained in:
Jonathan Turner 2009-06-11 02:16:03 +00:00
parent 72dc27f2da
commit d0ff0dc0f1
5 changed files with 58 additions and 12 deletions

View File

@ -115,7 +115,7 @@ bool pod_less_than(Boxed_POD_Value l, Boxed_POD_Value r)
{
return l < r;
}
template<typename P1, typename P2>
bool greater_than(P1 p1, P2 p2)
{
@ -126,7 +126,7 @@ bool pod_greater_than(Boxed_POD_Value l, Boxed_POD_Value r)
{
return l > r;
}
template<typename P1, typename P2>
bool less_than_equals(P1 p1, P2 p2)
{
@ -163,7 +163,7 @@ P1 &timesequal_pod(P1 &p1, Boxed_POD_Value r)
return (p1 *= r.d);
} else {
return (p1 *= r.i);
}
}
}
@ -181,7 +181,7 @@ P1 &dividesequal_pod(P1 &p1, Boxed_POD_Value r)
return (p1 /= r.d);
} else {
return (p1 /= r.i);
}
}
}
@ -199,7 +199,7 @@ P1 &addsequal_pod(P1 &p1, Boxed_POD_Value r)
return (p1 += r.d);
} else {
return (p1 += r.i);
}
}
}
template<typename P1, typename P2>
@ -216,7 +216,7 @@ P1 &subtractsequal_pod(P1 &p1, Boxed_POD_Value r)
return (p1 -= r.d);
} else {
return (p1 -= r.i);
}
}
}
template<typename P1>
@ -348,7 +348,7 @@ void add_opers_arithmetic_pod(BoxedCPP_System &s)
register_function(s, &pod_divide, "/");
register_function(s, &pod_multiply, "*");
}
template<typename T>
void add_opers_comparison(BoxedCPP_System &s)
{
@ -460,10 +460,28 @@ void bootstrap_pod_type(BoxedCPP_System &s, const std::string &name)
register_function(s, &to_string<T>, "to_string");
}
/*
void print(const std::string &s)
{
std::cout << s << std::endl;
}
*/
template <typename T>
void print(const T &t)
{
std::cout << t << std::endl;
}
template<> void print<bool>(const bool &t)
{
if (t) {
std::cout << "true" << std::endl;
}
else {
std::cout << "false" << std::endl;
}
}
void bootstrap(BoxedCPP_System &s)
{
@ -493,7 +511,11 @@ void bootstrap(BoxedCPP_System &s)
add_oper_add<std::string>(s);
add_oper_add_equals <std::string>(s);
register_function(s, &print, "print");
register_function(s, &print<int>, "print");
register_function(s, &print<std::string>, "print");
register_function(s, &print<double>, "print");
register_function(s, &print<float>, "print");
register_function(s, &print<bool>, "print");
s.register_function(boost::function<void ()>(boost::bind(&dump_system, boost::ref(s))), "dump_system");
s.register_function(boost::function<void (Boxed_Value)>(boost::bind(&dump_object, _1)), "dump_object");

3
samples/lambda.wes Normal file
View File

@ -0,0 +1,3 @@
var add_them = function(x, y) { x + y }
//print(add_them(3, 4))
print(7)

View File

@ -14,14 +14,14 @@
class TokenType { public: enum Type { File, Whitespace, Identifier, Integer, Operator, Parens_Open, Parens_Close,
Square_Open, Square_Close, Curly_Open, Curly_Close, Comma, Quoted_String, Single_Quoted_String, Carriage_Return, Semicolon,
Function_Def, Scoped_Block, Statement, Equation, Return, Expression, Term, Factor, Negate, Comment,
Function_Def, Lambda_Def, Scoped_Block, Statement, Equation, Return, Expression, Term, Factor, Negate, Comment,
Value, Fun_Call, Method_Call, Comparison, If_Block, While_Block, Boolean, Real_Number, Array_Call, Variable_Decl, Array_Init,
For_Block, Prefix, Break }; };
const char *tokentype_to_string(int tokentype) {
const char *token_types[] = {"File", "Whitespace", "Identifier", "Integer", "Operator", "Parens_Open", "Parens_Close",
"Square_Open", "Square_Close", "Curly_Open", "Curly_Close", "Comma", "Quoted_String", "Single_Quoted_String", "Carriage_Return", "Semicolon",
"Function_Def", "Scoped_Block", "Statement", "Equation", "Return", "Expression", "Term", "Factor", "Negate", "Comment",
"Function_Def", "Lambda_Def", "Scoped_Block", "Statement", "Equation", "Return", "Expression", "Term", "Factor", "Negate", "Comment",
"Value", "Fun_Call", "Method_Call", "Comparison", "If_Block", "While_Block", "Boolean", "Real Number", "Array_Call", "Variable_Decl", "Array_Init",
"For_Block", "Prefix", "Break" };

View File

@ -102,6 +102,7 @@ public:
Rule params;
Rule block(TokenType::Scoped_Block);
Rule fundef(TokenType::Function_Def);
Rule lambda_def(TokenType::Lambda_Def);
Rule statement;
Rule equation(TokenType::Equation);
Rule boolean(TokenType::Boolean);
@ -160,7 +161,7 @@ public:
expression = term >> *((Str("+") >> term) | (Str("-") >> term));
term = factor >> *((Str("*") >> factor) | (Str("/") >> factor));
factor = methodcall | arraycall | value | negate | prefix | (Ign(Str("+")) >> value);
value = vardecl | arrayinit | block | paren_block | return_statement | break_statement |
value = vardecl | arrayinit | block | paren_block | lambda_def | return_statement | break_statement |
funcall | Id(TokenType::Identifier) | Id(TokenType::Real_Number) | Id(TokenType::Integer) | Id(TokenType::Quoted_String) |
Id(TokenType::Single_Quoted_String) ;
@ -175,6 +176,7 @@ public:
return_statement = Ign(Str("return")) >> ~boolean;
break_statement = Wrap(Ign(Str("break")));
paren_block = (Ign(Id(TokenType::Parens_Open)) >> equation >> Ign(Id(TokenType::Parens_Close)));
lambda_def = Ign(Str("function")) >> ~(Ign(Id(TokenType::Parens_Open)) >> ~params >> Ign(Id(TokenType::Parens_Close))) >> block;
return rule;
}

View File

@ -186,20 +186,27 @@ Boxed_Value eval_token(Eval_System &ss, TokenPtr node) {
}
break;
case (TokenType::Fun_Call) : {
//BoxedCPP_System::Stack prev_stack = ss.set_stack(BoxedCPP_System::Stack());
Param_List_Builder plb;
for (i = 1; i < node->children.size(); ++i) {
plb << eval_token(ss, node->children[i]);
}
try {
retval = dispatch(ss.get_function(node->children[0]->text), plb);
//ss.set_stack(prev_stack);
}
catch(EvalError &ee) {
//ss.set_stack(prev_stack);
throw EvalError(ee.reason, node->children[0]);
}
catch(std::exception &e){
throw EvalError("Can not find appropriate '" + node->children[0]->text + "'", node->children[0]);
//ss.set_stack(prev_stack);
throw EvalError("Engine error: " + std::string(e.what()), node->children[0]);
}
catch(ReturnValue &rv) {
//ss.set_stack(prev_stack);
retval = rv.retval;
}
}
@ -349,6 +356,18 @@ Boxed_Value eval_token(Eval_System &ss, TokenPtr node) {
new Dynamic_Proxy_Function(boost::bind(&eval_function<Eval_System>, boost::ref(ss), node->children.back(), param_names, _1))), node->children[0]->text);
}
break;
case (TokenType::Lambda_Def) : {
unsigned int num_args = node->children.size() - 1;
std::vector<std::string> param_names;
for (i = 0; i < num_args; ++i) {
param_names.push_back(node->children[i]->text);
}
//retval = boost::shared_ptr<Proxy_Function>(new Proxy_Function_Impl<boost::function<void (const std::string &)> >(&test));
retval = Boxed_Value(boost::shared_ptr<Proxy_Function>(new Dynamic_Proxy_Function(
boost::bind(&eval_function<Eval_System>, boost::ref(ss), node->children.back(), param_names, _1))));
}
break;
case (TokenType::Scoped_Block) : {
ss.new_scope();
for (i = 0; i < node->children.size(); ++i) {