static
| 429 | |
| 430 | // static |
| 431 | TypedExprPtr Expressions::tryResolveCallWithLambdas( |
| 432 | const std::shared_ptr<const CallExpr>& callExpr, |
| 433 | const TypePtr& inputRow, |
| 434 | memory::MemoryPool* pool) { |
| 435 | auto signature = findLambdaSignature(callExpr); |
| 436 | |
| 437 | if (signature == nullptr) { |
| 438 | return nullptr; |
| 439 | } |
| 440 | |
| 441 | // Resolve non-lambda arguments first. |
| 442 | auto numArgs = callExpr->getInputs().size(); |
| 443 | std::vector<TypedExprPtr> children(numArgs); |
| 444 | std::vector<TypePtr> childTypes(numArgs); |
| 445 | for (auto i = 0; i < numArgs; ++i) { |
| 446 | if (!isLambdaArgument(signature->argumentTypes()[i])) { |
| 447 | children[i] = inferTypes(callExpr->getInputs()[i], inputRow, pool); |
| 448 | childTypes[i] = children[i]->type(); |
| 449 | } |
| 450 | } |
| 451 | |
| 452 | // Resolve lambda arguments. |
| 453 | exec::SignatureBinder binder(*signature, childTypes); |
| 454 | binder.tryBind(); |
| 455 | for (auto i = 0; i < numArgs; ++i) { |
| 456 | auto argSignature = signature->argumentTypes()[i]; |
| 457 | if (isLambdaArgument(argSignature)) { |
| 458 | std::vector<TypePtr> lambdaTypes; |
| 459 | for (auto j = 0; j < argSignature.parameters().size() - 1; ++j) { |
| 460 | auto type = binder.tryResolveType(argSignature.parameters()[j]); |
| 461 | if (type == nullptr) { |
| 462 | return nullptr; |
| 463 | } |
| 464 | lambdaTypes.push_back(type); |
| 465 | } |
| 466 | |
| 467 | children[i] = |
| 468 | inferTypes(callExpr->getInputs()[i], inputRow, lambdaTypes, pool); |
| 469 | } |
| 470 | } |
| 471 | |
| 472 | return createWithImplicitCast(callExpr, std::move(children)); |
| 473 | } |
| 474 | |
| 475 | // This method returns null if the expression doesn't depend on any input row. |
| 476 | TypePtr Expressions::getInputRowType(const TypedExprPtr& expr) { |
nothing calls this directly
no test coverage detected