mirror of
https://github.com/yhirose/cpp-peglib.git
synced 2025-01-22 21:35:29 +00:00
Interpolated string support.
This commit is contained in:
parent
8d2aeabb32
commit
456ce928ea
@ -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…
Reference in New Issue
Block a user