From 7ac784e73b026ce7e17babb2f0b819864fd898b0 Mon Sep 17 00:00:00 2001 From: Li Jin Date: Mon, 19 Apr 2021 18:10:08 +0800 Subject: rename BackcallOperator to PipeOperator. --- spec/inputs/backcall.yue | 84 +----------------------------------------- spec/inputs/loops.yue | 2 + spec/inputs/pipe.yue | 84 ++++++++++++++++++++++++++++++++++++++++++ src/yuescript/yue_ast.h | 16 ++++---- src/yuescript/yue_compiler.cpp | 52 +++++++++++++------------- src/yuescript/yue_parser.cpp | 16 ++++---- src/yuescript/yue_parser.h | 8 ++-- src/yuescript/yuescript.h | 56 +++++++++++++++++++++------- 8 files changed, 176 insertions(+), 142 deletions(-) create mode 100644 spec/inputs/pipe.yue diff --git a/spec/inputs/backcall.yue b/spec/inputs/backcall.yue index bad3a56..d7ed0dd 100644 --- a/spec/inputs/backcall.yue +++ b/spec/inputs/backcall.yue @@ -1,77 +1,3 @@ - -{"abc", 123, 998} |> foreach print - -{1,2,3} - |> map (x)-> x * 2 - |> filter (x)-> x > 4 - |> reduce 0, (a,b)-> a + b - |> print - -[i |> tostring for i = 0,10] |> table.concat(",") |> print - -b = 1 + 2 + (4 |> tostring |> print(1) or 123) - -if x = 233 |> math.max 998 - print x - -with b |> create? "new" - .value = 123 - print \work! - -123 |> f? - -"abc" |> f1? |> f2? - -c = "abc" |> f1? |> f2? - -f = -> - arg |> x.y?\if - -998 |> func2 "abc", 233 |> func0 |> func1 -998 |> func0("abc", 233) |> func1 |> func2 - -1 |> f 2, 3, 4, 5 -val(2) |> f 1, _, 3, 4, 5 -arr[3] |> f 1, 2, _, 4, 5 - -a = {"1","2","3"} |> table.concat("") |> tonumber |> f1(1, 2, 3, _) |> f2(1, _, 3) - -readFile("example.txt") |> - extract(_, language, {}) |> - parse(_, language) |> - emit |> - render |> - print - -readFile("example.txt") \ - |> extract(_, language, {}) \ - |> parse(_, language) \ - |> emit \ - |> render \ - |> print - -readFile "example.txt" - |> extract _, language, {} - |> parse _, language - |> emit - |> render - |> print - -123 |> not func! |> f - -do - _1 = list{"abc","xyz","123"}\map"#"\value! - |> -func! - |> abc 123, _, "x" - - global _2,_3,_4 = 1,2,3 - |> f - - local _5 = v |> f1 1 - |> f2 2 - |> f3 3 - |> f4 4 - do (x)<- map {1,2,3} x * 2 @@ -96,7 +22,7 @@ do do <- syncStatus - (err,data="nil")<- loadAsync "file.moon" + (err, data="nil")<- loadAsync "file.yue" if err print err return @@ -141,13 +67,5 @@ propB = do alert "hi" -x = 123 |> a |> b or 456 |> c |> d or a.if\then("abc") or a?.b\c?(123) or x\y - -x1 = 3 * -4 |> f - -x2 = 3 * -2 ^ 2 |> f - -y = 1 + not # 2 |> (a ^ c) |> b(3,_) * 4 ^ -123 |> f |> f1 or 123 - nil diff --git a/spec/inputs/loops.yue b/spec/inputs/loops.yue index 8946a2f..5708809 100644 --- a/spec/inputs/loops.yue +++ b/spec/inputs/loops.yue @@ -30,6 +30,8 @@ for x in y, z for x in y, z, k print x +for name, members in *modules + print name, member x = -> for x in y diff --git a/spec/inputs/pipe.yue b/spec/inputs/pipe.yue new file mode 100644 index 0000000..7e33422 --- /dev/null +++ b/spec/inputs/pipe.yue @@ -0,0 +1,84 @@ + +{"abc", 123, 998} |> foreach print + +{1,2,3} + |> map (x)-> x * 2 + |> filter (x)-> x > 4 + |> reduce 0, (a,b)-> a + b + |> print + +[i |> tostring for i = 0,10] |> table.concat(",") |> print + +b = 1 + 2 + (4 |> tostring |> print(1) or 123) + +if x = 233 |> math.max 998 + print x + +with b |> create? "new" + .value = 123 + print \work! + +123 |> f? + +"abc" |> f1? |> f2? + +c = "abc" |> f1? |> f2? + +f = -> + arg |> x.y?\if + +998 |> func2 "abc", 233 |> func0 |> func1 +998 |> func0("abc", 233) |> func1 |> func2 + +1 |> f 2, 3, 4, 5 +val(2) |> f 1, _, 3, 4, 5 +arr[3] |> f 1, 2, _, 4, 5 + +a = {"1","2","3"} |> table.concat("") |> tonumber |> f1(1, 2, 3, _) |> f2(1, _, 3) + +readFile("example.txt") |> + extract(_, language, {}) |> + parse(_, language) |> + emit |> + render |> + print + +readFile("example.txt") \ + |> extract(_, language, {}) \ + |> parse(_, language) \ + |> emit \ + |> render \ + |> print + +readFile "example.txt" + |> extract _, language, {} + |> parse _, language + |> emit + |> render + |> print + +123 |> not func! |> f + +do + _1 = list{"abc","xyz","123"}\map"#"\value! + |> -func! + |> abc 123, _, "x" + + global _2,_3,_4 = 1,2,3 + |> f + + local _5 = v |> f1 1 + |> f2 2 + |> f3 3 + |> f4 4 + +x = 123 |> a |> b or 456 |> c |> d or a.if\then("abc") or a?.b\c?(123) or x\y + +x1 = 3 * -4 |> f + +x2 = 3 * -2 ^ 2 |> f + +y = 1 + not # 2 |> (a ^ c) |> b(3,_) * 4 ^ -123 |> f |> f1 or 123 + +nil + diff --git a/src/yuescript/yue_ast.h b/src/yuescript/yue_ast.h index 4c33759..1e95d11 100644 --- a/src/yuescript/yue_ast.h +++ b/src/yuescript/yue_ast.h @@ -391,15 +391,15 @@ class unary_exp_t; AST_NODE(exp_op_value) ast_ptr op; - ast_list backcalls; - AST_MEMBER(exp_op_value, &op, &backcalls) + ast_list pipeExprs; + AST_MEMBER(exp_op_value, &op, &pipeExprs) AST_END(exp_op_value) AST_NODE(Exp) ast_ptr sep; - ast_list backcalls; + ast_list pipeExprs; ast_list opValues; - AST_MEMBER(Exp, &sep, &backcalls, &opValues) + AST_MEMBER(Exp, &sep, &pipeExprs, &opValues) AST_END(Exp) class Parens_t; @@ -727,11 +727,11 @@ AST_END(unless_line) AST_LEAF(BreakLoop) AST_END(BreakLoop) -AST_NODE(BackcallBody) +AST_NODE(PipeBody) ast_ptr sep; ast_list values; - AST_MEMBER(BackcallBody, &sep, &values) -AST_END(BackcallBody) + AST_MEMBER(PipeBody, &sep, &values) +AST_END(PipeBody) AST_NODE(statement_appendix) ast_sel item; @@ -744,7 +744,7 @@ AST_END(statement_sep) AST_NODE(Statement) ast_sel content; + Label_t, Goto_t, Backcall_t, LocalAttrib_t, PipeBody_t, ExpListAssign_t> content; ast_ptr appendix; ast_ptr needSep; AST_MEMBER(Statement, &content, &appendix, &needSep) diff --git a/src/yuescript/yue_compiler.cpp b/src/yuescript/yue_compiler.cpp index caa5b9e..85744d5 100644 --- a/src/yuescript/yue_compiler.cpp +++ b/src/yuescript/yue_compiler.cpp @@ -59,7 +59,7 @@ inline std::string s(std::string_view sv) { return std::string(sv); } -const std::string_view version = "0.7.6"sv; +const std::string_view version = "0.7.7"sv; const std::string_view extension = "yue"sv; class YueCompilerImpl { @@ -467,8 +467,8 @@ private: if (!exp) return nullptr; BLOCK_START BREAK_IF(!exp->opValues.empty()); - BREAK_IF(exp->backcalls.size() != 1); - auto unary = static_cast(exp->backcalls.back()); + BREAK_IF(exp->pipeExprs.size() != 1); + auto unary = static_cast(exp->pipeExprs.back()); BREAK_IF(unary->expos.size() != 1); return unary; BLOCK_END @@ -488,7 +488,7 @@ private: auto unary = x->new_ptr(); unary->expos.push_back(value); auto exp = x->new_ptr(); - exp->backcalls.push_back(unary); + exp->pipeExprs.push_back(unary); return exp; } @@ -500,17 +500,17 @@ private: auto runary = x->new_ptr(); runary->expos.push_back(right); opValue->op.set(op); - opValue->backcalls.push_back(runary); + opValue->pipeExprs.push_back(runary); } auto exp = x->new_ptr(); - exp->backcalls.push_back(lunary); + exp->pipeExprs.push_back(lunary); exp->opValues.push_back(opValue); return exp; } ast_ptr newExp(unary_exp_t* unary, ast_node* x) { auto exp = x->new_ptr(); - exp->backcalls.push_back(unary); + exp->pipeExprs.push_back(unary); return exp; } @@ -785,7 +785,7 @@ private: } bool isPureBackcall(Exp_t* exp) const { - return exp->opValues.empty() && exp->backcalls.size() > 1; + return exp->opValues.empty() && exp->pipeExprs.size() > 1; } bool isMacroChain(ChainValue_t* chainValue) const { @@ -923,7 +923,7 @@ private: case id(): transformLabel(static_cast(content), out); break; case id(): transformGoto(static_cast(content), out); break; case id(): transformLocalAttrib(static_cast(content), out); break; - case id(): throw std::logic_error(_info.errorMessage("backcall chain must be following a value"sv, x)); break; + case id(): throw std::logic_error(_info.errorMessage("pipe chain must be following a value"sv, x)); break; case id(): { auto expListAssign = static_cast(content); if (expListAssign->action) { @@ -1955,7 +1955,7 @@ private: out.push_back(join(temp, ", "sv)); } - void transform_backcall_exp(const node_container& values, str_list& out, ExpUsage usage, ExpList_t* assignList = nullptr) { + void transform_pipe_exp(const node_container& values, str_list& out, ExpUsage usage, ExpList_t* assignList = nullptr) { if (values.size() == 1 && usage == ExpUsage::Closure) { transform_unary_exp(static_cast(values.front()), out); } else { @@ -1968,7 +1968,7 @@ private: if (values.back() == *it && !unary->ops.empty() && usage == ExpUsage::Common) { throw std::logic_error(_info.errorMessage("expression list is not supported here"sv, x)); } - if (!value) throw std::logic_error(_info.errorMessage("backcall operator must be followed by chain value"sv, *it)); + if (!value) throw std::logic_error(_info.errorMessage("pipe operator must be followed by chain value"sv, *it)); if (auto chainValue = value->item.as()) { if (isChainValueCall(chainValue)) { auto last = chainValue->items.back(); @@ -1989,7 +1989,7 @@ private: args->swap(a, arg); findPlaceHolder = true; } else { - throw std::logic_error(_info.errorMessage("backcall placeholder can be used only in one place"sv, a)); + throw std::logic_error(_info.errorMessage("pipe placeholder can be used only in one place"sv, a)); } } } @@ -2003,7 +2003,7 @@ private: } arg.set(newExp(unary, x)); } else { - throw std::logic_error(_info.errorMessage("backcall operator must be followed by chain value"sv, value)); + throw std::logic_error(_info.errorMessage("pipe operator must be followed by chain value"sv, value)); } } switch (usage) { @@ -2046,18 +2046,18 @@ private: void transformExp(Exp_t* exp, str_list& out, ExpUsage usage, ExpList_t* assignList = nullptr) { if (exp->opValues.empty()) { - transform_backcall_exp(exp->backcalls.objects(), out, usage, assignList); + transform_pipe_exp(exp->pipeExprs.objects(), out, usage, assignList); return; } if (usage != ExpUsage::Closure) { YUEE("invalid expression usage", exp); } str_list temp; - transform_backcall_exp(exp->backcalls.objects(), temp, ExpUsage::Closure); + transform_pipe_exp(exp->pipeExprs.objects(), temp, ExpUsage::Closure); for (auto _opValue : exp->opValues.objects()) { auto opValue = static_cast(_opValue); transformBinaryOperator(opValue->op, temp); - transform_backcall_exp(opValue->backcalls.objects(), temp, ExpUsage::Closure); + transform_pipe_exp(opValue->pipeExprs.objects(), temp, ExpUsage::Closure); } out.push_back(join(temp, " "sv)); } @@ -2206,7 +2206,7 @@ private: for (auto it = nodes.begin(); it != nodes.end(); ++it) { auto node = *it; auto stmt = static_cast(node); - if (auto backcallBody = stmt->content.as()) { + if (auto pipeBody = stmt->content.as()) { auto x = stmt; bool cond = false; BLOCK_START @@ -2214,7 +2214,7 @@ private: auto last = it; --last; auto lst = static_cast(*last); if (lst->appendix) { - throw std::logic_error(_info.errorMessage("statement decorator must be placed at the end of backcall chain"sv, lst->appendix.get())); + throw std::logic_error(_info.errorMessage("statement decorator must be placed at the end of pipe chain"sv, lst->appendix.get())); } lst->appendix.set(stmt->appendix); stmt->appendix.set(nullptr); @@ -2222,18 +2222,18 @@ private: stmt->needSep.set(nullptr); auto exp = lastExpFromStatement(lst); BREAK_IF(!exp); - for (auto val : backcallBody->values.objects()) { - exp->backcalls.push_back(val); + for (auto val : pipeBody->values.objects()) { + exp->pipeExprs.push_back(val); } cond = true; BLOCK_END - if (!cond) throw std::logic_error(_info.errorMessage("backcall chain must be following a value"sv, x)); + if (!cond) throw std::logic_error(_info.errorMessage("pipe chain must be following a value"sv, x)); stmt->content.set(nullptr); auto next = it; ++next; BLOCK_START BREAK_IF(next == nodes.end()); - BREAK_IF(!static_cast(*next)->content.as()); - throw std::logic_error(_info.errorMessage("indent mismatch in backcall chain"sv, *next)); + BREAK_IF(!static_cast(*next)->content.as()); + throw std::logic_error(_info.errorMessage("indent mismatch in pipe chain"sv, *next)); BLOCK_END } else if (auto backcall = stmt->content.as()) { auto x = *nodes.begin(); @@ -3513,7 +3513,7 @@ private: for (auto arg : *args) { std::string str; // check whether arg is reassembled - // do some workaround for backcall expression + // do some workaround for pipe expression if (ast_is(arg) && arg->m_begin.m_it == arg->m_end.m_it) { auto exp = static_cast(arg); BLOCK_START @@ -3525,10 +3525,10 @@ private: str = std::get<1>(expandMacroStr(chainValue)); BLOCK_END if (str.empty()) { - // exp is reassembled due to backcall expressions + // exp is reassembled due to pipe expressions // in transform stage, toString(exp) won't be able // to convert its whole text content - str = _parser.toString(exp->backcalls.front()); + str = _parser.toString(exp->pipeExprs.front()); } } else if (auto lstr = ast_cast(arg)) { str = _parser.toString(lstr->content); diff --git a/src/yuescript/yue_parser.cpp b/src/yuescript/yue_parser.cpp index c76b574..30c5598 100644 --- a/src/yuescript/yue_parser.cpp +++ b/src/yuescript/yue_parser.cpp @@ -333,9 +333,9 @@ YueParser::YueParser() { expr("not") >> not_(AlphaNum); unary_exp = *(Space >> unary_operator) >> expo_exp; - BackcallOperator = expr("|>"); - backcall_value = Space >> BackcallOperator >> *SpaceBreak >> unary_exp; - backcall_exp = unary_exp >> *backcall_value; + PipeOperator = expr("|>"); + pipe_value = Space >> PipeOperator >> *SpaceBreak >> unary_exp; + pipe_exp = unary_exp >> *pipe_value; BinaryOperator = (expr("or") >> not_(AlphaNum)) | @@ -350,8 +350,8 @@ YueParser::YueParser() { expr(">>") | expr("//") | set("+-*/%><|&~"); - exp_op_value = Space >> BinaryOperator >> *SpaceBreak >> backcall_exp; - Exp = Seperator >> backcall_exp >> *exp_op_value; + exp_op_value = Space >> BinaryOperator >> *SpaceBreak >> pipe_exp; + Exp = Seperator >> pipe_exp >> *exp_op_value; DisableChain = pl::user(true_(), [](const item_t& item) { State* st = reinterpret_cast(item.user_data); @@ -563,7 +563,7 @@ YueParser::YueParser() { fn_arrow_back = expr('<') >> set("-="); Backcall = -FnArgsDef >> Space >> fn_arrow_back >> Space >> ChainValue; - BackcallBody = Seperator >> Space >> BackcallOperator >> unary_exp >> *(+SpaceBreak >> CheckIndent >> Space >> BackcallOperator >> unary_exp); + PipeBody = Seperator >> Space >> PipeOperator >> unary_exp >> *(+SpaceBreak >> CheckIndent >> Space >> PipeOperator >> unary_exp); ExpList = Seperator >> Exp >> *(sym(',') >> Exp); ExpListLow = Seperator >> Exp >> *(Space >> set(",;") >> Exp); @@ -605,14 +605,14 @@ YueParser::YueParser() { Import | While | Repeat | For | ForEach | Return | Local | Global | Export | Macro | Space >> BreakLoop | Label | Goto | Backcall | - LocalAttrib | BackcallBody | ExpListAssign + LocalAttrib | PipeBody | ExpListAssign ) >> Space >> -statement_appendix >> -statement_sep; Body = InBlock | Statement; empty_line_stop = Space >> and_(Break); - Line = and_(check_indent >> Space >> not_(BackcallOperator)) >> Statement | Advance >> ensure(and_(Space >> BackcallOperator) >> Statement, PopIndent) | empty_line_stop; + Line = and_(check_indent >> Space >> not_(PipeOperator)) >> Statement | Advance >> ensure(and_(Space >> PipeOperator) >> Statement, PopIndent) | empty_line_stop; Block = Seperator >> Line >> *(+Break >> Line); Shebang = expr("#!") >> *(not_(Stop) >> Any); diff --git a/src/yuescript/yue_parser.h b/src/yuescript/yue_parser.h index a614d01..cb9cfba 100644 --- a/src/yuescript/yue_parser.h +++ b/src/yuescript/yue_parser.h @@ -175,10 +175,10 @@ private: rule ArgLine; rule ArgBlock; rule invoke_args_with_table; - rule BackcallOperator; + rule PipeOperator; rule ExponentialOperator; - rule backcall_value; - rule backcall_exp; + rule pipe_value; + rule pipe_exp; rule expo_value; rule expo_exp; rule empty_line_stop; @@ -216,7 +216,7 @@ private: AST_RULE(Goto) AST_RULE(fn_arrow_back) AST_RULE(Backcall) - AST_RULE(BackcallBody) + AST_RULE(PipeBody) AST_RULE(ExpListLow) AST_RULE(ExpList) AST_RULE(Return) diff --git a/src/yuescript/yuescript.h b/src/yuescript/yuescript.h index cdbfd57..6fc9c20 100644 --- a/src/yuescript/yuescript.h +++ b/src/yuescript/yuescript.h @@ -214,18 +214,48 @@ setmetatable(yue, { return self.require(name) end }) -for k, v in pairs({ - insert_loader = insert_loader, - remove_loader = remove_loader, - loader = yue_loader, - dofile = dofile, - loadfile = loadfile, - loadstring = loadstring, - create_yuepath = create_yuepath, - find_modulepath = find_modulepath, - pcall = yue_call, - require = yue_require -}) do - yue[k] = v +local function dump(what) + local seen = { } + local _dump + _dump = function(what, depth) + depth = depth or 0 + local t = type(what) + if "string" == t then + return "\"" .. tostring(what) .. "\"\n" + elseif "table" == t then + if seen[what] then + return "recursion(" .. tostring(what) .. ")...\n" + end + seen[what] = true + depth = depth + 1 + local lines = {} + for k, v in pairs(what) do + insert(lines, ('\t'):rep(depth) .. "[" .. tostring(k) .. "] = " .. _dump(v, depth)) + end + seen[what] = false + return "{\n" .. concat(lines) .. ('\t'):rep(depth - 1) .. "}\n" + else + return tostring(what) .. "\n" + end + end + return _dump(what) +end +local function p(...) + local args = {...} + for i = 1, #args do + args[i] = dump(args[i]) + end + print(concat(args)) end +yue.insert_loader = insert_loader +yue.remove_loader = remove_loader +yue.loader = yue_loader +yue.dofile = dofile +yue.loadfile = loadfile +yue.loadstring = loadstring +yue.create_yuepath = create_yuepath +yue.find_modulepath = find_modulepath +yue.pcall = yue_call +yue.require = yue_require +yue.p = p )yuescript_codes"; -- cgit v1.2.3-55-g6feb