Interpolated string support.

pull/3/head
yhirose 9 years ago
parent 8d2aeabb32
commit 456ce928ea
  1. 10
      language/interpreter.cc
  2. 15
      language/interpreter.hpp
  3. 7
      language/parser.cc
  4. 3
      language/parser.hpp

@ -20,6 +20,7 @@ struct Eval
case Identifier: return eval_identifier(ast, env);
case Number: return eval_number(ast, env);
case Boolean: return eval_bool(ast, env);
case InterpolatedString: return eval_interpolated_string(ast, env);
}
if (ast.is_token) {
@ -174,6 +175,15 @@ private:
return Value(ast.token == "true");
};
static Value eval_interpolated_string(const Ast& ast, Env& env) {
string s;
for (auto node: ast.nodes) {
const auto& val = eval(*node, env);
s += val.str();
}
return Value(s);
};
static Value dereference_identirier(Env& env, const string& var) {
if (!env.has(var)) {
string msg = "undefined variable '" + var + "'...";

@ -61,6 +61,19 @@ struct Value
throw std::runtime_error("type error.");
}
std::string str() const {
switch (type) {
case Undefined: return "undefined";
case Bool: return to_bool() ? "true" : "false";
case Long: return std::to_string(to_long()); break;
case String: return to_string();
//case Function: return "[function]";
//case Array: return "[array]";
default: throw std::logic_error("invalid internal condition.");
}
// NOTREACHED
}
std::ostream& out(std::ostream& os) const {
switch (type) {
case Undefined: os << "undefined"; break;
@ -181,7 +194,7 @@ struct Env
auto func_pretty_print = Value::FunctionValue {
{ "arg" },
[](Env& env) {
std::cout << env.get("arg") << std::endl;
std::cout << env.get("arg").str() << std::endl;
return Value();
}
};

@ -20,7 +20,7 @@ static auto g_grammar = R"(
PRIMARY <- CONDITION (CONDITION_OPERATOR CONDITION)?
CONDITION <- TERM (TERM_OPERATOR TERM)*
TERM <- FACTOR (FACTOR_OPERATOR FACTOR)*
FACTOR <- WHILE / IF / FUNCTION / FUNCTION_CALL / NUMBER / BOOLEAN / STRING / IDENTIFIER / '(' _ EXPRESSION ')' _
FACTOR <- WHILE / IF / FUNCTION / FUNCTION_CALL / NUMBER / BOOLEAN / STRING / INTERPOLATED_STRING / IDENTIFIER / '(' _ EXPRESSION ')' _
BLOCK <- '{' _ STATEMENTS '}' _
@ -33,6 +33,9 @@ static auto g_grammar = R"(
BOOLEAN <- < ('true' / 'false') > _
STRING <- ['] < (!['] .)* > ['] _
INTERPOLATED_STRING <- '"' ('{' _ EXPRESSION '}' / INTERPOLATED_CONTENT)* '"' _
INTERPOLATED_CONTENT <- (!["{] .) (!["{] .)*
~_ <- (Space / EndOfLine / Comment)*
Space <- ' ' / '\t'
EndOfLine <- '\r\n' / '\n' / '\r'
@ -76,6 +79,8 @@ peglib::peg& get_parser()
.ast_token("BOOLEAN", Boolean)
.ast_token("STRING")
.ast_token("IDENTIFIER", Identifier)
.ast_node("INTERPOLATED_STRING", InterpolatedString)
.ast_token("INTERPOLATED_CONTENT")
.ast_end();
}

@ -3,7 +3,8 @@
enum AstType
{
Statements, While, If, FunctionCall, Assignment, Condition, BinExpresion,
Identifier, Number, Boolean, Function
Identifier, InterpolatedString,
Number, Boolean, Function
};
peglib::peg& get_parser();

Loading…
Cancel
Save