diff options
Diffstat (limited to '')
| -rw-r--r-- | spec/inputs/destructure.yue | 10 | ||||
| -rw-r--r-- | spec/inputs/funcs.yue | 4 | ||||
| -rw-r--r-- | spec/inputs/string.yue | 4 | ||||
| -rw-r--r-- | spec/inputs/unicode/funcs.yue | 2 | ||||
| -rw-r--r-- | spec/inputs/unicode/vararg.yue | 4 | ||||
| -rw-r--r-- | spec/inputs/vararg.yue | 4 | ||||
| -rw-r--r-- | spec/inputs/with.yue | 4 | ||||
| -rw-r--r-- | spec/outputs/destructure.lua | 20 | ||||
| -rw-r--r-- | spec/outputs/string.lua | 2 | ||||
| -rw-r--r-- | src/yuescript/yue_ast.h | 2 | ||||
| -rw-r--r-- | src/yuescript/yue_compiler.cpp | 26 | ||||
| -rw-r--r-- | src/yuescript/yue_parser.cpp | 46 | ||||
| -rw-r--r-- | src/yuescript/yue_parser.h | 1 |
13 files changed, 89 insertions, 40 deletions
diff --git a/spec/inputs/destructure.yue b/spec/inputs/destructure.yue index b6250d0..179056c 100644 --- a/spec/inputs/destructure.yue +++ b/spec/inputs/destructure.yue | |||
| @@ -278,5 +278,15 @@ do | |||
| 278 | do | 278 | do |
| 279 | {a, :abc, b, :def, ...sub, d, e} = tb | 279 | {a, :abc, b, :def, ...sub, d, e} = tb |
| 280 | 280 | ||
| 281 | do | ||
| 282 | for {:a, :b} in *items | ||
| 283 | print a, b | ||
| 284 | |||
| 285 | for :a, :b in *items | ||
| 286 | print a, b | ||
| 287 | |||
| 288 | for :body in pairs data | ||
| 289 | print body if body | ||
| 290 | |||
| 281 | nil | 291 | nil |
| 282 | 292 | ||
diff --git a/spec/inputs/funcs.yue b/spec/inputs/funcs.yue index 6b1669b..d19c2d1 100644 --- a/spec/inputs/funcs.yue +++ b/spec/inputs/funcs.yue | |||
| @@ -98,7 +98,7 @@ f( | |||
| 98 | 98 | ||
| 99 | x = (a, | 99 | x = (a, |
| 100 | b) -> | 100 | b) -> |
| 101 | print "what" | 101 | print "what" |
| 102 | 102 | ||
| 103 | 103 | ||
| 104 | y = (a="hi", | 104 | y = (a="hi", |
| @@ -211,7 +211,7 @@ do | |||
| 211 | print "kv:", k, v | 211 | print "kv:", k, v |
| 212 | print "rest count:", select "#", ... | 212 | print "rest count:", select "#", ... |
| 213 | macro gen = (fname) -> | | 213 | macro gen = (fname) -> | |
| 214 | #{fname} = ({:a, :b = 0}) -> print a, b | 214 | #{fname} = ({:a, :b = 0}) -> print a, b |
| 215 | $gen foo | 215 | $gen foo |
| 216 | t1 = (:a, x) -> print a, x | 216 | t1 = (:a, x) -> print a, x |
| 217 | t2 = (:a) -> print a | 217 | t2 = (:a) -> print a |
diff --git a/spec/inputs/string.yue b/spec/inputs/string.yue index 1f0fba8..611205d 100644 --- a/spec/inputs/string.yue +++ b/spec/inputs/string.yue | |||
| @@ -100,8 +100,8 @@ do | |||
| 100 | next: 123 | 100 | next: 123 |
| 101 | str = | | 101 | str = | |
| 102 | list: | 102 | list: |
| 103 | - "one" | 103 | - "one" |
| 104 | - "two" | 104 | - "two" |
| 105 | str = | | 105 | str = | |
| 106 | -- comment | 106 | -- comment |
| 107 | content text | 107 | content text |
diff --git a/spec/inputs/unicode/funcs.yue b/spec/inputs/unicode/funcs.yue index c563356..cb35500 100644 --- a/spec/inputs/unicode/funcs.yue +++ b/spec/inputs/unicode/funcs.yue | |||
| @@ -98,7 +98,7 @@ _无效变量 = -> 真名 if 某物 | |||
| 98 | 98 | ||
| 99 | 变量x = (参数a, | 99 | 变量x = (参数a, |
| 100 | 参数b) -> | 100 | 参数b) -> |
| 101 | 打印 "什么" | 101 | 打印 "什么" |
| 102 | 102 | ||
| 103 | 103 | ||
| 104 | 变量y = (参数a="hi", | 104 | 变量y = (参数a="hi", |
diff --git a/spec/inputs/unicode/vararg.yue b/spec/inputs/unicode/vararg.yue index e59e114..b508fbb 100644 --- a/spec/inputs/unicode/vararg.yue +++ b/spec/inputs/unicode/vararg.yue | |||
| @@ -55,12 +55,12 @@ | |||
| 55 | _ = -> | 55 | _ = -> |
| 56 | 列表 = {1, 2, 3, 4, 5} | 56 | 列表 = {1, 2, 3, 4, 5} |
| 57 | 函数名 = (确定) -> | 57 | 函数名 = (确定) -> |
| 58 | 确定, table.unpack 列表 | 58 | 确定, table.unpack 列表 |
| 59 | 确定, ... = 函数名 true | 59 | 确定, ... = 函数名 true |
| 60 | 打印 确定, ... | 60 | 打印 确定, ... |
| 61 | 61 | ||
| 62 | 多参数函数 = -> | 62 | 多参数函数 = -> |
| 63 | 10, nil, 20, nil, 30 | 63 | 10, nil, 20, nil, 30 |
| 64 | 64 | ||
| 65 | ... = 多参数函数! | 65 | ... = 多参数函数! |
| 66 | 打印 select "#", ... | 66 | 打印 select "#", ... |
diff --git a/spec/inputs/vararg.yue b/spec/inputs/vararg.yue index 941cd97..6100250 100644 --- a/spec/inputs/vararg.yue +++ b/spec/inputs/vararg.yue | |||
| @@ -55,12 +55,12 @@ join = (...) -> | |||
| 55 | _ = -> | 55 | _ = -> |
| 56 | list = {1, 2, 3, 4, 5} | 56 | list = {1, 2, 3, 4, 5} |
| 57 | fn = (ok) -> | 57 | fn = (ok) -> |
| 58 | ok, table.unpack list | 58 | ok, table.unpack list |
| 59 | ok, ... = fn true | 59 | ok, ... = fn true |
| 60 | print ok, ... | 60 | print ok, ... |
| 61 | 61 | ||
| 62 | fn_many_args = -> | 62 | fn_many_args = -> |
| 63 | 10, nil, 20, nil, 30 | 63 | 10, nil, 20, nil, 30 |
| 64 | 64 | ||
| 65 | ... = fn_many_args! | 65 | ... = fn_many_args! |
| 66 | print select "#", ... | 66 | print select "#", ... |
diff --git a/spec/inputs/with.yue b/spec/inputs/with.yue index 2256833..19ed2a7 100644 --- a/spec/inputs/with.yue +++ b/spec/inputs/with.yue | |||
| @@ -167,7 +167,7 @@ do | |||
| 167 | 167 | ||
| 168 | do | 168 | do |
| 169 | a = for i = 1, 100 | 169 | a = for i = 1, 100 |
| 170 | with? x := tb[i] | 170 | with? x := tb[i] |
| 171 | break x if .id := 1 | 171 | break x if .id := 1 |
| 172 | 172 | ||
| 173 | nil | 173 | nil |
diff --git a/spec/outputs/destructure.lua b/spec/outputs/destructure.lua index ba216b5..4e19aca 100644 --- a/spec/outputs/destructure.lua +++ b/spec/outputs/destructure.lua | |||
| @@ -711,4 +711,24 @@ do | |||
| 711 | return _accum_0 | 711 | return _accum_0 |
| 712 | end)(), _obj_0[#_obj_0 - 1], _obj_0[#_obj_0] | 712 | end)(), _obj_0[#_obj_0 - 1], _obj_0[#_obj_0] |
| 713 | end | 713 | end |
| 714 | do | ||
| 715 | local _list_0 = items | ||
| 716 | for _index_0 = 1, #_list_0 do | ||
| 717 | local _des_0 = _list_0[_index_0] | ||
| 718 | local a, b = _des_0.a, _des_0.b | ||
| 719 | print(a, b) | ||
| 720 | end | ||
| 721 | local _list_1 = items | ||
| 722 | for _index_0 = 1, #_list_1 do | ||
| 723 | local _des_0 = _list_1[_index_0] | ||
| 724 | local a, b = _des_0.a, _des_0.b | ||
| 725 | print(a, b) | ||
| 726 | end | ||
| 727 | for _des_0 in pairs(data) do | ||
| 728 | local body = _des_0.body | ||
| 729 | if body then | ||
| 730 | print(body) | ||
| 731 | end | ||
| 732 | end | ||
| 733 | end | ||
| 714 | return nil | 734 | return nil |
diff --git a/spec/outputs/string.lua b/spec/outputs/string.lua index b536e6d..bdfd676 100644 --- a/spec/outputs/string.lua +++ b/spec/outputs/string.lua | |||
| @@ -52,7 +52,7 @@ do | |||
| 52 | str = "user: " .. tostring(name) .. "\nid: " .. tostring(id) | 52 | str = "user: " .. tostring(name) .. "\nid: " .. tostring(id) |
| 53 | str = "path: \"C:\\\\Program Files\\\\App\"\ndesc: 'single \"quote\" test'" | 53 | str = "path: \"C:\\\\Program Files\\\\App\"\ndesc: 'single \"quote\" test'" |
| 54 | str = "key: value \nnext: 123 " | 54 | str = "key: value \nnext: 123 " |
| 55 | str = "list:\n - \"one\"\n - \"two\"" | 55 | str = "list:\n\t- \"one\"\n\t- \"two\"" |
| 56 | str = "-- comment\ncontent text\n-- comment" | 56 | str = "-- comment\ncontent text\n-- comment" |
| 57 | str = tostring(1 + 2) .. '\n' .. tostring(2 + 3) .. '\n' .. tostring("a" .. "b") | 57 | str = tostring(1 + 2) .. '\n' .. tostring(2 + 3) .. '\n' .. tostring("a" .. "b") |
| 58 | local obj = { | 58 | local obj = { |
diff --git a/src/yuescript/yue_ast.h b/src/yuescript/yue_ast.h index 0008fd6..5f04fa0 100644 --- a/src/yuescript/yue_ast.h +++ b/src/yuescript/yue_ast.h | |||
| @@ -848,7 +848,7 @@ AST_NODE(Macro) | |||
| 848 | AST_END(Macro) | 848 | AST_END(Macro) |
| 849 | 849 | ||
| 850 | AST_NODE(NameOrDestructure) | 850 | AST_NODE(NameOrDestructure) |
| 851 | ast_sel<true, Variable_t, TableLit_t, Comprehension_t> item; | 851 | ast_sel<true, Variable_t, SimpleTable_t, TableLit_t, Comprehension_t> item; |
| 852 | AST_MEMBER(NameOrDestructure, &item) | 852 | AST_MEMBER(NameOrDestructure, &item) |
| 853 | AST_END(NameOrDestructure) | 853 | AST_END(NameOrDestructure) |
| 854 | 854 | ||
diff --git a/src/yuescript/yue_compiler.cpp b/src/yuescript/yue_compiler.cpp index d6db3fc..55ab4ec 100644 --- a/src/yuescript/yue_compiler.cpp +++ b/src/yuescript/yue_compiler.cpp | |||
| @@ -78,7 +78,7 @@ static std::unordered_set<std::string> Metamethods = { | |||
| 78 | "close"s // Lua 5.4 | 78 | "close"s // Lua 5.4 |
| 79 | }; | 79 | }; |
| 80 | 80 | ||
| 81 | const std::string_view version = "0.29.8"sv; | 81 | const std::string_view version = "0.29.9"sv; |
| 82 | const std::string_view extension = "yue"sv; | 82 | const std::string_view extension = "yue"sv; |
| 83 | 83 | ||
| 84 | class CompileError : public std::logic_error { | 84 | class CompileError : public std::logic_error { |
| @@ -8427,13 +8427,8 @@ private: | |||
| 8427 | varConstAfter = vars.back(); | 8427 | varConstAfter = vars.back(); |
| 8428 | } | 8428 | } |
| 8429 | break; | 8429 | break; |
| 8430 | case id<TableLit_t>(): { | 8430 | case id<SimpleTable_t>(): |
| 8431 | auto desVar = getUnusedName("_des_"sv); | 8431 | case id<TableLit_t>(): |
| 8432 | destructPairs.emplace_back(item, toAst<Exp_t>(desVar, x)); | ||
| 8433 | vars.push_back(desVar); | ||
| 8434 | varAfter.push_back(desVar); | ||
| 8435 | break; | ||
| 8436 | } | ||
| 8437 | case id<Comprehension_t>(): { | 8432 | case id<Comprehension_t>(): { |
| 8438 | auto desVar = getUnusedName("_des_"sv); | 8433 | auto desVar = getUnusedName("_des_"sv); |
| 8439 | destructPairs.emplace_back(item, toAst<Exp_t>(desVar, x)); | 8434 | destructPairs.emplace_back(item, toAst<Exp_t>(desVar, x)); |
| @@ -8642,11 +8637,18 @@ private: | |||
| 8642 | if (!destructPairs.empty()) { | 8637 | if (!destructPairs.empty()) { |
| 8643 | temp.clear(); | 8638 | temp.clear(); |
| 8644 | for (auto& pair : destructPairs) { | 8639 | for (auto& pair : destructPairs) { |
| 8645 | auto sValue = x->new_ptr<SimpleValue_t>(); | ||
| 8646 | sValue->value.set(pair.first); | ||
| 8647 | auto exp = newExp(sValue, x); | ||
| 8648 | auto expList = x->new_ptr<ExpList_t>(); | 8640 | auto expList = x->new_ptr<ExpList_t>(); |
| 8649 | expList->exprs.push_back(exp); | 8641 | if (ast_is<SimpleTable_t>(pair.first)) { |
| 8642 | auto value = x->new_ptr<Value_t>(); | ||
| 8643 | value->item.set(pair.first); | ||
| 8644 | auto exp = newExp(value, x); | ||
| 8645 | expList->exprs.push_back(exp); | ||
| 8646 | } else { | ||
| 8647 | auto sValue = x->new_ptr<SimpleValue_t>(); | ||
| 8648 | sValue->value.set(pair.first); | ||
| 8649 | auto exp = newExp(sValue, x); | ||
| 8650 | expList->exprs.push_back(exp); | ||
| 8651 | } | ||
| 8650 | auto assign = x->new_ptr<Assign_t>(); | 8652 | auto assign = x->new_ptr<Assign_t>(); |
| 8651 | assign->values.push_back(pair.second); | 8653 | assign->values.push_back(pair.second); |
| 8652 | auto assignment = x->new_ptr<ExpListAssign_t>(); | 8654 | auto assignment = x->new_ptr<ExpListAssign_t>(); |
diff --git a/src/yuescript/yue_parser.cpp b/src/yuescript/yue_parser.cpp index fccb6fb..cbba115 100644 --- a/src/yuescript/yue_parser.cpp +++ b/src/yuescript/yue_parser.cpp | |||
| @@ -232,27 +232,43 @@ YueParser::YueParser() { | |||
| 232 | KeyName = SelfItem | Name | UnicodeName; | 232 | KeyName = SelfItem | Name | UnicodeName; |
| 233 | VarArg = "..."; | 233 | VarArg = "..."; |
| 234 | 234 | ||
| 235 | check_indent = pl::user(plain_space, [](const item_t& item) { | 235 | auto getIndent = [](const item_t& item) -> int { |
| 236 | if (item.begin->m_it == item.end->m_it) return 0; | ||
| 237 | State* st = reinterpret_cast<State*>(item.user_data); | ||
| 238 | bool useTab = false; | ||
| 239 | if (st->useTab) { | ||
| 240 | useTab = st->useTab.value(); | ||
| 241 | } else { | ||
| 242 | useTab = *item.begin->m_it == '\t'; | ||
| 243 | st->useTab = useTab; | ||
| 244 | } | ||
| 236 | int indent = 0; | 245 | int indent = 0; |
| 237 | for (input_it i = item.begin->m_it; i != item.end->m_it; ++i) { | 246 | if (useTab) { |
| 238 | switch (*i) { | 247 | for (input_it i = item.begin->m_it; i != item.end->m_it; ++i) { |
| 239 | case ' ': indent++; break; | 248 | switch (*i) { |
| 240 | case '\t': indent += 4; break; | 249 | case '\t': indent += 4; break; |
| 250 | default: throw ParserError("can not mix the use of tabs and spaces as indents"sv, item.begin); break; | ||
| 251 | } | ||
| 252 | } | ||
| 253 | } else { | ||
| 254 | for (input_it i = item.begin->m_it; i != item.end->m_it; ++i) { | ||
| 255 | switch (*i) { | ||
| 256 | case ' ': indent++; break; | ||
| 257 | default: throw ParserError("can not mix the use of tabs and spaces as indents"sv, item.begin); break; | ||
| 258 | } | ||
| 241 | } | 259 | } |
| 242 | } | 260 | } |
| 261 | return indent; | ||
| 262 | }; | ||
| 263 | |||
| 264 | check_indent = pl::user(plain_space, [getIndent](const item_t& item) { | ||
| 243 | State* st = reinterpret_cast<State*>(item.user_data); | 265 | State* st = reinterpret_cast<State*>(item.user_data); |
| 244 | return st->indents.top() == indent; | 266 | return st->indents.top() == getIndent(item); |
| 245 | }); | 267 | }); |
| 246 | check_indent_match = and_(check_indent); | 268 | check_indent_match = and_(check_indent); |
| 247 | 269 | ||
| 248 | advance = pl::user(plain_space, [](const item_t& item) { | 270 | advance = pl::user(plain_space, [getIndent](const item_t& item) { |
| 249 | int indent = 0; | 271 | int indent = getIndent(item); |
| 250 | for (input_it i = item.begin->m_it; i != item.end->m_it; ++i) { | ||
| 251 | switch (*i) { | ||
| 252 | case ' ': indent++; break; | ||
| 253 | case '\t': indent += 4; break; | ||
| 254 | } | ||
| 255 | } | ||
| 256 | State* st = reinterpret_cast<State*>(item.user_data); | 272 | State* st = reinterpret_cast<State*>(item.user_data); |
| 257 | int top = st->indents.top(); | 273 | int top = st->indents.top(); |
| 258 | if (top != -1 && indent > top) { | 274 | if (top != -1 && indent > top) { |
| @@ -921,7 +937,7 @@ YueParser::YueParser() { | |||
| 921 | MacroInPlace = '$' >> space >> "->" >> space >> Body; | 937 | MacroInPlace = '$' >> space >> "->" >> space >> Body; |
| 922 | 938 | ||
| 923 | NameList = Seperator >> Variable >> *(space >> ',' >> space >> Variable); | 939 | NameList = Seperator >> Variable >> *(space >> ',' >> space >> Variable); |
| 924 | NameOrDestructure = Variable | TableLit | Comprehension; | 940 | NameOrDestructure = Variable | TableLit | Comprehension | SimpleTable; |
| 925 | AssignableNameList = Seperator >> NameOrDestructure >> *(space >> ',' >> space >> NameOrDestructure); | 941 | AssignableNameList = Seperator >> NameOrDestructure >> *(space >> ',' >> space >> NameOrDestructure); |
| 926 | 942 | ||
| 927 | FnArrowBack = '<' >> set("-="); | 943 | FnArrowBack = '<' >> set("-="); |
diff --git a/src/yuescript/yue_parser.h b/src/yuescript/yue_parser.h index 4c546b1..d5c37e2 100644 --- a/src/yuescript/yue_parser.h +++ b/src/yuescript/yue_parser.h | |||
| @@ -119,6 +119,7 @@ protected: | |||
| 119 | int expLevel = 0; | 119 | int expLevel = 0; |
| 120 | size_t stringOpen = 0; | 120 | size_t stringOpen = 0; |
| 121 | std::string buffer; | 121 | std::string buffer; |
| 122 | std::optional<bool> useTab; | ||
| 122 | std::stack<int> indents; | 123 | std::stack<int> indents; |
| 123 | std::vector<bool> noDoStack; | 124 | std::vector<bool> noDoStack; |
| 124 | std::vector<bool> noChainBlockStack; | 125 | std::vector<bool> noChainBlockStack; |
