diff options
| -rw-r--r-- | spec/inputs/cond.yue | 22 | ||||
| -rw-r--r-- | spec/outputs/cond.lua | 155 | ||||
| -rw-r--r-- | spec/outputs/unicode/cond.lua | 12 | ||||
| -rw-r--r-- | src/yuescript/yue_compiler.cpp | 265 |
4 files changed, 349 insertions, 105 deletions
diff --git a/spec/inputs/cond.yue b/spec/inputs/cond.yue index df7d78e..f5f42a8 100644 --- a/spec/inputs/cond.yue +++ b/spec/inputs/cond.yue | |||
| @@ -237,6 +237,28 @@ do | |||
| 237 | 237 | ||
| 238 | evaluation = v(1) > v(2) <= v(3) | 238 | evaluation = v(1) > v(2) <= v(3) |
| 239 | 239 | ||
| 240 | do | ||
| 241 | a = v(1) < v(2) < v(3) < v(4) | ||
| 242 | a = x and y or v(1) < v(2) < v(3) < v(4) | ||
| 243 | a = v(1) < v(2) < v(3) < v(4) or x and y | ||
| 244 | a = x and y or v(1) < v(2) < v(3) < v(4) or w and z | ||
| 245 | |||
| 246 | a = v(1) < v(2) < v(3) and b < v(4) < v(5) < v(6) | ||
| 247 | a = x and y or v(1) < v(2) < v(3) and b < v(4) < v(5) < v(6) | ||
| 248 | a = v(1) < v(2) < v(3) and b < v(4) < v(5) < v(6) or x and y | ||
| 249 | a = x and y or v(1) < v(2) < v(3) and b < v(4) < v(5) < v(6) or w and z | ||
| 250 | |||
| 251 | local v1, v2, v3, v4, v5, v6 | ||
| 252 | a = v1 < v2 < v3 < v4 | ||
| 253 | a = x and y or v1 < v2 < v3 < v4 | ||
| 254 | a = v1 < v2 < v3 < v4 or x and y | ||
| 255 | a = x and y or v1 < v2 < v3 < v4 or w and z | ||
| 256 | |||
| 257 | a = v1 < v2 < v3 and b < v4 < v5 < v6 | ||
| 258 | a = x and y or v1 < v2 < v3 and b < v4 < v5 < v6 | ||
| 259 | a = v1 < v2 < v3 and b < v4 < v5 < v6 or x and y | ||
| 260 | a = x and y or v1 < v2 < v3 and b < v4 < v5 < v6 or w and z | ||
| 261 | |||
| 240 | nil | 262 | nil |
| 241 | 263 | ||
| 242 | 264 | ||
diff --git a/spec/outputs/cond.lua b/spec/outputs/cond.lua index 651c14a..d7aae02 100644 --- a/spec/outputs/cond.lua +++ b/spec/outputs/cond.lua | |||
| @@ -355,11 +355,162 @@ do | |||
| 355 | local evaluation | 355 | local evaluation |
| 356 | do | 356 | do |
| 357 | local _cond_0 = v(2) | 357 | local _cond_0 = v(2) |
| 358 | evaluation = v(1) < _cond_0 and _cond_0 <= v(3) | 358 | if not (v(1) < _cond_0) then |
| 359 | evaluation = false | ||
| 360 | else | ||
| 361 | evaluation = _cond_0 <= v(3) | ||
| 362 | end | ||
| 363 | end | ||
| 364 | do | ||
| 365 | local _cond_0 = v(2) | ||
| 366 | if not (v(1) > _cond_0) then | ||
| 367 | evaluation = false | ||
| 368 | else | ||
| 369 | evaluation = _cond_0 <= v(3) | ||
| 370 | end | ||
| 359 | end | 371 | end |
| 372 | end | ||
| 373 | do | ||
| 360 | do | 374 | do |
| 361 | local _cond_0 = v(2) | 375 | local _cond_0 = v(2) |
| 362 | evaluation = v(1) > _cond_0 and _cond_0 <= v(3) | 376 | if not (v(1) < _cond_0) then |
| 377 | a = false | ||
| 378 | else | ||
| 379 | local _cond_1 = v(3) | ||
| 380 | if not (_cond_0 < _cond_1) then | ||
| 381 | a = false | ||
| 382 | else | ||
| 383 | a = _cond_1 < v(4) | ||
| 384 | end | ||
| 385 | end | ||
| 363 | end | 386 | end |
| 387 | a = x and y or (function() | ||
| 388 | local _cond_0 = v(2) | ||
| 389 | if not (v(1) < _cond_0) then | ||
| 390 | return false | ||
| 391 | else | ||
| 392 | local _cond_1 = v(3) | ||
| 393 | if not (_cond_0 < _cond_1) then | ||
| 394 | return false | ||
| 395 | else | ||
| 396 | return _cond_1 < v(4) | ||
| 397 | end | ||
| 398 | end | ||
| 399 | end)() | ||
| 400 | a = (function() | ||
| 401 | local _cond_0 = v(2) | ||
| 402 | if not (v(1) < _cond_0) then | ||
| 403 | return false | ||
| 404 | else | ||
| 405 | local _cond_1 = v(3) | ||
| 406 | if not (_cond_0 < _cond_1) then | ||
| 407 | return false | ||
| 408 | else | ||
| 409 | return _cond_1 < v(4) | ||
| 410 | end | ||
| 411 | end | ||
| 412 | end)() or x and y | ||
| 413 | a = x and y or (function() | ||
| 414 | local _cond_0 = v(2) | ||
| 415 | if not (v(1) < _cond_0) then | ||
| 416 | return false | ||
| 417 | else | ||
| 418 | local _cond_1 = v(3) | ||
| 419 | if not (_cond_0 < _cond_1) then | ||
| 420 | return false | ||
| 421 | else | ||
| 422 | return _cond_1 < v(4) | ||
| 423 | end | ||
| 424 | end | ||
| 425 | end)() or w and z | ||
| 426 | a = (function() | ||
| 427 | local _cond_0 = v(2) | ||
| 428 | if not (v(1) < _cond_0) then | ||
| 429 | return false | ||
| 430 | else | ||
| 431 | return _cond_0 < v(3) | ||
| 432 | end | ||
| 433 | end)() and (function() | ||
| 434 | local _cond_0 = v(4) | ||
| 435 | if not (b < _cond_0) then | ||
| 436 | return false | ||
| 437 | else | ||
| 438 | local _cond_1 = v(5) | ||
| 439 | if not (_cond_0 < _cond_1) then | ||
| 440 | return false | ||
| 441 | else | ||
| 442 | return _cond_1 < v(6) | ||
| 443 | end | ||
| 444 | end | ||
| 445 | end)() | ||
| 446 | a = x and y or (function() | ||
| 447 | local _cond_0 = v(2) | ||
| 448 | if not (v(1) < _cond_0) then | ||
| 449 | return false | ||
| 450 | else | ||
| 451 | return _cond_0 < v(3) | ||
| 452 | end | ||
| 453 | end)() and (function() | ||
| 454 | local _cond_0 = v(4) | ||
| 455 | if not (b < _cond_0) then | ||
| 456 | return false | ||
| 457 | else | ||
| 458 | local _cond_1 = v(5) | ||
| 459 | if not (_cond_0 < _cond_1) then | ||
| 460 | return false | ||
| 461 | else | ||
| 462 | return _cond_1 < v(6) | ||
| 463 | end | ||
| 464 | end | ||
| 465 | end)() | ||
| 466 | a = (function() | ||
| 467 | local _cond_0 = v(2) | ||
| 468 | if not (v(1) < _cond_0) then | ||
| 469 | return false | ||
| 470 | else | ||
| 471 | return _cond_0 < v(3) | ||
| 472 | end | ||
| 473 | end)() and (function() | ||
| 474 | local _cond_0 = v(4) | ||
| 475 | if not (b < _cond_0) then | ||
| 476 | return false | ||
| 477 | else | ||
| 478 | local _cond_1 = v(5) | ||
| 479 | if not (_cond_0 < _cond_1) then | ||
| 480 | return false | ||
| 481 | else | ||
| 482 | return _cond_1 < v(6) | ||
| 483 | end | ||
| 484 | end | ||
| 485 | end)() or x and y | ||
| 486 | a = x and y or (function() | ||
| 487 | local _cond_0 = v(2) | ||
| 488 | if not (v(1) < _cond_0) then | ||
| 489 | return false | ||
| 490 | else | ||
| 491 | return _cond_0 < v(3) | ||
| 492 | end | ||
| 493 | end)() and (function() | ||
| 494 | local _cond_0 = v(4) | ||
| 495 | if not (b < _cond_0) then | ||
| 496 | return false | ||
| 497 | else | ||
| 498 | local _cond_1 = v(5) | ||
| 499 | if not (_cond_0 < _cond_1) then | ||
| 500 | return false | ||
| 501 | else | ||
| 502 | return _cond_1 < v(6) | ||
| 503 | end | ||
| 504 | end | ||
| 505 | end)() or w and z | ||
| 506 | local v1, v2, v3, v4, v5, v6 | ||
| 507 | a = v1 < v2 and v2 < v3 and v3 < v4 | ||
| 508 | a = x and y or v1 < v2 and v2 < v3 and v3 < v4 | ||
| 509 | a = v1 < v2 and v2 < v3 and v3 < v4 or x and y | ||
| 510 | a = x and y or v1 < v2 and v2 < v3 and v3 < v4 or w and z | ||
| 511 | a = v1 < v2 and v2 < v3 and b < v4 and v4 < v5 and v5 < v6 | ||
| 512 | a = x and y or v1 < v2 and v2 < v3 and b < v4 and v4 < v5 and v5 < v6 | ||
| 513 | a = v1 < v2 and v2 < v3 and b < v4 and v4 < v5 and v5 < v6 or x and y | ||
| 514 | a = x and y or v1 < v2 and v2 < v3 and b < v4 and v4 < v5 and v5 < v6 or w and z | ||
| 364 | end | 515 | end |
| 365 | return nil | 516 | return nil |
diff --git a/spec/outputs/unicode/cond.lua b/spec/outputs/unicode/cond.lua index 9a4ccb9..ed5d274 100644 --- a/spec/outputs/unicode/cond.lua +++ b/spec/outputs/unicode/cond.lua | |||
| @@ -361,11 +361,19 @@ do | |||
| 361 | local _u6c42_u503c | 361 | local _u6c42_u503c |
| 362 | do | 362 | do |
| 363 | local _cond_0 = _u503c(2) | 363 | local _cond_0 = _u503c(2) |
| 364 | _u6c42_u503c = _u503c(1) < _cond_0 and _cond_0 <= _u503c(3) | 364 | if not (_u503c(1) < _cond_0) then |
| 365 | _u6c42_u503c = false | ||
| 366 | else | ||
| 367 | _u6c42_u503c = _cond_0 <= _u503c(3) | ||
| 368 | end | ||
| 365 | end | 369 | end |
| 366 | do | 370 | do |
| 367 | local _cond_0 = _u503c(2) | 371 | local _cond_0 = _u503c(2) |
| 368 | _u6c42_u503c = _u503c(1) > _cond_0 and _cond_0 <= _u503c(3) | 372 | if not (_u503c(1) > _cond_0) then |
| 373 | _u6c42_u503c = false | ||
| 374 | else | ||
| 375 | _u6c42_u503c = _cond_0 <= _u503c(3) | ||
| 376 | end | ||
| 369 | end | 377 | end |
| 370 | end | 378 | end |
| 371 | return nil | 379 | return nil |
diff --git a/src/yuescript/yue_compiler.cpp b/src/yuescript/yue_compiler.cpp index d32d9c1..7ec3b3a 100644 --- a/src/yuescript/yue_compiler.cpp +++ b/src/yuescript/yue_compiler.cpp | |||
| @@ -75,7 +75,7 @@ static std::unordered_set<std::string> Metamethods = { | |||
| 75 | "close"s // Lua 5.4 | 75 | "close"s // Lua 5.4 |
| 76 | }; | 76 | }; |
| 77 | 77 | ||
| 78 | const std::string_view version = "0.20.0"sv; | 78 | const std::string_view version = "0.20.1"sv; |
| 79 | const std::string_view extension = "yue"sv; | 79 | const std::string_view extension = "yue"sv; |
| 80 | 80 | ||
| 81 | class CompileError : public std::logic_error { | 81 | class CompileError : public std::logic_error { |
| @@ -1207,19 +1207,16 @@ private: | |||
| 1207 | 1207 | ||
| 1208 | bool isConditionChaining(Exp_t* exp) { | 1208 | bool isConditionChaining(Exp_t* exp) { |
| 1209 | int conditionChaining = 0; | 1209 | int conditionChaining = 0; |
| 1210 | for (const auto& opValue_ : exp->opValues.objects()) { | 1210 | for (auto opValue_ : exp->opValues.objects()) { |
| 1211 | auto opValue = static_cast<ExpOpValue_t*>(opValue_); | 1211 | auto opValue = static_cast<ExpOpValue_t*>(opValue_); |
| 1212 | auto op = _parser.toString(opValue->op); | 1212 | auto op = _parser.toString(opValue->op); |
| 1213 | if (isConditionChainingOperator(op)) { | 1213 | if (isConditionChainingOperator(op)) { |
| 1214 | conditionChaining++; | 1214 | conditionChaining++; |
| 1215 | if (conditionChaining > 1) { | 1215 | } else if (conditionChaining > 0) { |
| 1216 | return true; | 1216 | return false; |
| 1217 | } | ||
| 1218 | } else { | ||
| 1219 | conditionChaining = 0; | ||
| 1220 | } | 1217 | } |
| 1221 | } | 1218 | } |
| 1222 | return false; | 1219 | return conditionChaining > 1 && conditionChaining == static_cast<int>(exp->opValues.size()); |
| 1223 | } | 1220 | } |
| 1224 | 1221 | ||
| 1225 | UnaryExp_t* unaryGeneratingAnonFunc(Exp_t* exp) { | 1222 | UnaryExp_t* unaryGeneratingAnonFunc(Exp_t* exp) { |
| @@ -3369,14 +3366,14 @@ private: | |||
| 3369 | std::list<std::pair<std::string, ast_list<true, UnaryExp_t>*>> chains; | 3366 | std::list<std::pair<std::string, ast_list<true, UnaryExp_t>*>> chains; |
| 3370 | chains.emplace_back(std::string(), &exp->pipeExprs); | 3367 | chains.emplace_back(std::string(), &exp->pipeExprs); |
| 3371 | int conditionChainCount = 0; | 3368 | int conditionChainCount = 0; |
| 3372 | str_list evalLines; | 3369 | auto checkChains = [&]()-> ast_ptr<false, Exp_t> { |
| 3373 | auto checkChains = [&]() { | ||
| 3374 | std::optional<str_list> result; | 3370 | std::optional<str_list> result; |
| 3375 | if (conditionChainCount > 1) { | 3371 | if (conditionChainCount > 1) { |
| 3376 | bool needWrapping = false; | 3372 | ast_ptr<false, Exp_t> newCondExp; |
| 3377 | str_list conds; | 3373 | ast_ptr<false, ExpListAssign_t> preDefine; |
| 3378 | str_list preDefines; | 3374 | ast_sel_list<true, IfCond_t, Block_t, Statement_t>* nodes = nullptr; |
| 3379 | std::list<std::variant<std::string, ast_ptr<false, Exp_t>>> stack; | 3375 | std::list<std::variant<std::string, ast_list<true, UnaryExp_t>>> stack; |
| 3376 | pushScope(); | ||
| 3380 | for (const auto& item : chains) { | 3377 | for (const auto& item : chains) { |
| 3381 | if (!item.first.empty()) { | 3378 | if (!item.first.empty()) { |
| 3382 | stack.push_back(item.first); | 3379 | stack.push_back(item.first); |
| @@ -3393,9 +3390,7 @@ private: | |||
| 3393 | if (varName.empty()) { | 3390 | if (varName.empty()) { |
| 3394 | if (auto sval = static_cast<Value_t*>(unary->expos.front())->item.as<SimpleValue_t>()) { | 3391 | if (auto sval = static_cast<Value_t*>(unary->expos.front())->item.as<SimpleValue_t>()) { |
| 3395 | if (ast_is<ConstValue_t, Num_t>(sval->value)) { | 3392 | if (ast_is<ConstValue_t, Num_t>(sval->value)) { |
| 3396 | auto condExp = unary->new_ptr<Exp_t>(); | 3393 | stack.push_back(*item.second); |
| 3397 | condExp->pipeExprs.dup(*item.second); | ||
| 3398 | stack.push_back(condExp); | ||
| 3399 | goto reduce; | 3394 | goto reduce; |
| 3400 | } | 3395 | } |
| 3401 | } | 3396 | } |
| @@ -3404,77 +3399,125 @@ private: | |||
| 3404 | } | 3399 | } |
| 3405 | if (varName.empty() || !isLocal(varName)) { | 3400 | if (varName.empty() || !isLocal(varName)) { |
| 3406 | varName = getUnusedName("_cond_"sv); | 3401 | varName = getUnusedName("_cond_"sv); |
| 3402 | addToScope(varName); | ||
| 3407 | auto condExp = node->new_ptr<Exp_t>(); | 3403 | auto condExp = node->new_ptr<Exp_t>(); |
| 3408 | condExp->pipeExprs.dup(*item.second); | 3404 | condExp->pipeExprs.dup(*item.second); |
| 3409 | auto varExp = toAst<Exp_t>(varName, node); | 3405 | auto varExp = toAst<Exp_t>(varName, node); |
| 3410 | auto assignment = assignmentFrom(varExp, condExp, node); | 3406 | auto assignment = assignmentFrom(varExp, condExp, node); |
| 3411 | if (!needWrapping) { | 3407 | preDefine = assignment; |
| 3412 | needWrapping = true; | 3408 | stack.push_back(varExp->pipeExprs); |
| 3413 | if (usage == ExpUsage::Closure) { | ||
| 3414 | pushFunctionScope(); | ||
| 3415 | pushAnonVarArg(); | ||
| 3416 | pushScope(); | ||
| 3417 | } else if (usage == ExpUsage::Assignment) { | ||
| 3418 | pushScope(); | ||
| 3419 | } | ||
| 3420 | } | ||
| 3421 | transformAssignment(assignment, preDefines); | ||
| 3422 | stack.push_back(varExp); | ||
| 3423 | goto reduce; | 3409 | goto reduce; |
| 3424 | } | 3410 | } |
| 3425 | } | 3411 | } |
| 3426 | { | 3412 | { |
| 3427 | auto condExp = node->new_ptr<Exp_t>(); | 3413 | stack.push_back(*item.second); |
| 3428 | condExp->pipeExprs.dup(*item.second); | ||
| 3429 | stack.push_back(condExp); | ||
| 3430 | } | 3414 | } |
| 3431 | reduce: | 3415 | reduce: { |
| 3432 | if (stack.size() == 3) { | 3416 | if (stack.size() == 3) { |
| 3433 | str_list tmp; | 3417 | auto condExp = exp->new_ptr<Exp_t>(); |
| 3434 | auto one = std::get<ast_ptr<false, Exp_t>>(stack.front()).get(); | 3418 | const auto& one = std::get<ast_list<true, UnaryExp_t>>(stack.front()); |
| 3435 | transformExp(one, tmp, ExpUsage::Closure); | 3419 | condExp->pipeExprs.dup(one); |
| 3436 | stack.pop_front(); | 3420 | stack.pop_front(); |
| 3437 | auto two = std::get<std::string>(stack.front()); | 3421 | auto opValue = exp->new_ptr<ExpOpValue_t>(); |
| 3438 | tmp.push_back(two); | 3422 | const auto& two = std::get<std::string>(stack.front()); |
| 3423 | auto op = toAst<BinaryOperator_t>(two, exp); | ||
| 3424 | opValue->op.set(op); | ||
| 3439 | stack.pop_front(); | 3425 | stack.pop_front(); |
| 3440 | auto three = std::get<ast_ptr<false, Exp_t>>(stack.front()).get(); | 3426 | const auto& three = std::get<ast_list<true, UnaryExp_t>>(stack.front()); |
| 3441 | transformExp(three, tmp, ExpUsage::Closure); | 3427 | opValue->pipeExprs.dup(three); |
| 3442 | conds.push_back(join(tmp, " "sv)); | 3428 | condExp->opValues.push_back(opValue); |
| 3443 | } | 3429 | if (preDefine) { |
| 3444 | } | 3430 | auto ifNode = exp->new_ptr<If_t>(); |
| 3445 | auto condStr = join(conds, " and "sv); | 3431 | ifNode->type.set(toAst<IfType_t>("unless"sv, exp)); |
| 3446 | if (needWrapping && usage == ExpUsage::Closure) { | 3432 | auto ifCond = exp->new_ptr<IfCond_t>(); |
| 3447 | str_list closureLines{anonFuncStart() + nll(exp)}; | 3433 | ifCond->condition.set(condExp); |
| 3448 | closureLines.insert(closureLines.end(), preDefines.begin(), preDefines.end()); | 3434 | ifNode->nodes.push_back(ifCond); |
| 3449 | closureLines.push_back(indent() + "return "s + condStr + nll(exp)); | 3435 | ifNode->nodes.push_back(toAst<Statement_t>("false"sv, exp)); |
| 3450 | popScope(); | 3436 | if (newCondExp) { |
| 3451 | closureLines.push_back(indent() + anonFuncEnd()); | 3437 | if (nodes) { |
| 3452 | temp.push_back(join(closureLines)); | 3438 | auto block = exp->new_ptr<Block_t>(); |
| 3453 | popAnonVarArg(); | 3439 | auto stmt = exp->new_ptr<Statement_t>(); |
| 3454 | popFunctionScope(); | 3440 | stmt->content.set(preDefine); |
| 3455 | } else { | 3441 | preDefine.set(nullptr); |
| 3456 | temp.push_back(condStr); | 3442 | block->statements.push_back(stmt); |
| 3457 | if (!preDefines.empty()) { | 3443 | auto simpleValue = exp->new_ptr<SimpleValue_t>(); |
| 3458 | evalLines.insert(evalLines.end(), preDefines.begin(), preDefines.end()); | 3444 | simpleValue->value.set(ifNode); |
| 3459 | if (usage == ExpUsage::Assignment) { | 3445 | auto explist = exp->new_ptr<ExpList_t>(); |
| 3460 | popScope(); | 3446 | explist->exprs.push_back(newExp(simpleValue, exp)); |
| 3447 | auto expListAssign = exp->new_ptr<ExpListAssign_t>(); | ||
| 3448 | expListAssign->expList.set(explist); | ||
| 3449 | stmt = exp->new_ptr<Statement_t>(); | ||
| 3450 | stmt->content.set(expListAssign); | ||
| 3451 | block->statements.push_back(stmt); | ||
| 3452 | nodes->push_back(block); | ||
| 3453 | nodes = &ifNode->nodes; | ||
| 3454 | } else { | ||
| 3455 | auto ifNodePrev = exp->new_ptr<If_t>(); | ||
| 3456 | ifNodePrev->type.set(toAst<IfType_t>("unless"sv, exp)); | ||
| 3457 | auto ifCondPrev = exp->new_ptr<IfCond_t>(); | ||
| 3458 | ifCondPrev->condition.set(newCondExp); | ||
| 3459 | ifNodePrev->nodes.push_back(ifCondPrev); | ||
| 3460 | ifNodePrev->nodes.push_back(toAst<Statement_t>("false", exp)); | ||
| 3461 | auto simpleValue = exp->new_ptr<SimpleValue_t>(); | ||
| 3462 | simpleValue->value.set(ifNodePrev); | ||
| 3463 | newCondExp.set(newExp(simpleValue, exp)); | ||
| 3464 | nodes = &ifNodePrev->nodes; | ||
| 3465 | } | ||
| 3466 | } else { | ||
| 3467 | auto block = exp->new_ptr<Block_t>(); | ||
| 3468 | auto stmt = exp->new_ptr<Statement_t>(); | ||
| 3469 | stmt->content.set(preDefine); | ||
| 3470 | preDefine.set(nullptr); | ||
| 3471 | block->statements.push_back(stmt); | ||
| 3472 | auto simpleValue = exp->new_ptr<SimpleValue_t>(); | ||
| 3473 | simpleValue->value.set(ifNode); | ||
| 3474 | auto explist = exp->new_ptr<ExpList_t>(); | ||
| 3475 | explist->exprs.push_back(newExp(simpleValue, exp)); | ||
| 3476 | auto expListAssign = exp->new_ptr<ExpListAssign_t>(); | ||
| 3477 | expListAssign->expList.set(explist); | ||
| 3478 | stmt = exp->new_ptr<Statement_t>(); | ||
| 3479 | stmt->content.set(expListAssign); | ||
| 3480 | block->statements.push_back(stmt); | ||
| 3481 | auto body = exp->new_ptr<Body_t>(); | ||
| 3482 | body->content.set(block); | ||
| 3483 | auto doNode = exp->new_ptr<Do_t>(); | ||
| 3484 | doNode->body.set(body); | ||
| 3485 | simpleValue = exp->new_ptr<SimpleValue_t>(); | ||
| 3486 | simpleValue->value.set(doNode); | ||
| 3487 | newCondExp.set(newExp(simpleValue, exp)); | ||
| 3488 | nodes = &ifNode->nodes; | ||
| 3489 | } | ||
| 3490 | } else { | ||
| 3491 | if (newCondExp) { | ||
| 3492 | if (nodes) { | ||
| 3493 | auto explist = exp->new_ptr<ExpList_t>(); | ||
| 3494 | explist->exprs.push_back(condExp); | ||
| 3495 | auto expListAssign = exp->new_ptr<ExpListAssign_t>(); | ||
| 3496 | expListAssign->expList.set(explist); | ||
| 3497 | auto stmt = exp->new_ptr<Statement_t>(); | ||
| 3498 | stmt->content.set(expListAssign); | ||
| 3499 | nodes->push_back(stmt); | ||
| 3500 | } else { | ||
| 3501 | auto opValue = exp->new_ptr<ExpOpValue_t>(); | ||
| 3502 | opValue->op.set(toAst<BinaryOperator_t>("and"sv, exp)); | ||
| 3503 | opValue->pipeExprs.dup(condExp->pipeExprs); | ||
| 3504 | newCondExp->opValues.push_back(opValue); | ||
| 3505 | newCondExp->opValues.dup(condExp->opValues); | ||
| 3506 | } | ||
| 3507 | } else { | ||
| 3508 | newCondExp.set(condExp); | ||
| 3509 | } | ||
| 3510 | } | ||
| 3461 | } | 3511 | } |
| 3462 | } | 3512 | } |
| 3463 | } | 3513 | } |
| 3464 | } else { | 3514 | popScope(); |
| 3465 | for (const auto& item : chains) { | 3515 | return newCondExp; |
| 3466 | if (!item.first.empty()) { | ||
| 3467 | temp.push_back(item.first); | ||
| 3468 | } | ||
| 3469 | transform_pipe_exp(item.second->objects(), temp, ExpUsage::Closure); | ||
| 3470 | } | ||
| 3471 | } | 3516 | } |
| 3472 | conditionChainCount = 0; | 3517 | return nullptr; |
| 3473 | chains.clear(); | ||
| 3474 | }; | 3518 | }; |
| 3475 | str_list preDefines; | 3519 | for (auto opValue_ : exp->opValues.objects()) { |
| 3476 | for (auto _opValue : exp->opValues.objects()) { | 3520 | auto opValue = static_cast<ExpOpValue_t*>(opValue_); |
| 3477 | auto opValue = static_cast<ExpOpValue_t*>(_opValue); | ||
| 3478 | transformBinaryOperator(opValue->op, temp); | 3521 | transformBinaryOperator(opValue->op, temp); |
| 3479 | auto op = temp.back(); | 3522 | auto op = temp.back(); |
| 3480 | temp.pop_back(); | 3523 | temp.pop_back(); |
| @@ -3482,43 +3525,63 @@ private: | |||
| 3482 | conditionChainCount++; | 3525 | conditionChainCount++; |
| 3483 | chains.emplace_back(op, &opValue->pipeExprs); | 3526 | chains.emplace_back(op, &opValue->pipeExprs); |
| 3484 | } else { | 3527 | } else { |
| 3485 | checkChains(); | 3528 | if (auto e = checkChains()) { |
| 3529 | transformExp(e, temp, ExpUsage::Closure); | ||
| 3530 | } else { | ||
| 3531 | for (const auto& item : chains) { | ||
| 3532 | if (!item.first.empty()) { | ||
| 3533 | temp.push_back(item.first); | ||
| 3534 | } | ||
| 3535 | transform_pipe_exp(item.second->objects(), temp, ExpUsage::Closure); | ||
| 3536 | } | ||
| 3537 | } | ||
| 3538 | chains.clear(); | ||
| 3539 | conditionChainCount = 0; | ||
| 3486 | temp.push_back(op); | 3540 | temp.push_back(op); |
| 3487 | transform_pipe_exp(opValue->pipeExprs.objects(), temp, ExpUsage::Closure); | 3541 | chains.emplace_back(Empty, &opValue->pipeExprs); |
| 3488 | } | 3542 | } |
| 3489 | } | 3543 | } |
| 3490 | checkChains(); | 3544 | if (auto e = checkChains()) { |
| 3491 | auto condStr = join(temp, " "sv); | 3545 | if (!temp.empty()) { |
| 3492 | switch (usage) { | 3546 | transformExp(e, temp, ExpUsage::Closure); |
| 3493 | case ExpUsage::Closure: { | 3547 | auto condStr = join(temp, " "sv); |
| 3494 | out.push_back(condStr); | 3548 | out.push_back(condStr); |
| 3495 | break; | 3549 | } else { |
| 3496 | } | 3550 | switch (usage) { |
| 3497 | case ExpUsage::Assignment: { | 3551 | case ExpUsage::Closure: |
| 3498 | auto assignment = exp->new_ptr<ExpListAssign_t>(); | 3552 | transformExp(e, out, ExpUsage::Closure); |
| 3499 | assignment->expList.set(assignList); | 3553 | break; |
| 3500 | auto assign = exp->new_ptr<Assign_t>(); | 3554 | case ExpUsage::Assignment: { |
| 3501 | assign->values.push_back(toAst<Exp_t>(condStr, exp)); | 3555 | auto assignment = exp->new_ptr<ExpListAssign_t>(); |
| 3502 | assignment->action.set(assign); | 3556 | assignment->expList.set(assignList); |
| 3503 | if (evalLines.empty()) { | 3557 | auto assign = exp->new_ptr<Assign_t>(); |
| 3504 | transformAssignment(assignment, out); | 3558 | assign->values.push_back(e); |
| 3505 | } else { | 3559 | assignment->action.set(assign); |
| 3506 | evalLines.push_front(indent() + "do"s + nll(exp)); | 3560 | transformAssignment(assignment, out); |
| 3507 | evalLines.push_front(getPreDefineLine(assignment)); | 3561 | break; |
| 3508 | pushScope(); | 3562 | } |
| 3509 | transformAssignment(assignment, evalLines); | 3563 | case ExpUsage::Return: { |
| 3510 | popScope(); | 3564 | auto expListLow = exp->new_ptr<ExpListLow_t>(); |
| 3511 | evalLines.push_back(indent() + "end"s + nlr(exp)); | 3565 | expListLow->exprs.push_back(e); |
| 3512 | out.push_back(join(evalLines)); | 3566 | auto returnNode = exp->new_ptr<Return_t>(); |
| 3567 | returnNode->valueList.set(expListLow); | ||
| 3568 | transformReturn(returnNode, out); | ||
| 3569 | break; | ||
| 3570 | } | ||
| 3571 | default: | ||
| 3572 | YUEE("invalid expression usage", exp); | ||
| 3573 | break; | ||
| 3513 | } | 3574 | } |
| 3514 | break; | ||
| 3515 | } | 3575 | } |
| 3516 | case ExpUsage::Return: { | 3576 | } else { |
| 3517 | evalLines.push_back(indent() + "return "s + condStr + nll(exp)); | 3577 | for (const auto& item : chains) { |
| 3518 | out.push_back(join(evalLines)); | 3578 | if (!item.first.empty()) { |
| 3519 | break; | 3579 | temp.push_back(item.first); |
| 3580 | } | ||
| 3581 | transform_pipe_exp(item.second->objects(), temp, ExpUsage::Closure); | ||
| 3520 | } | 3582 | } |
| 3521 | default: YUEE("invalid expression usage", exp); break; | 3583 | auto condStr = join(temp, " "sv); |
| 3584 | out.push_back(condStr); | ||
| 3522 | } | 3585 | } |
| 3523 | } | 3586 | } |
| 3524 | 3587 | ||
