aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authora-romanov <Anton.Romanov@ydb.tech>2023-04-24 11:28:33 +0300
committera-romanov <Anton.Romanov@ydb.tech>2023-04-24 11:28:33 +0300
commitf9a0c8229df295ad699d1395f7f5c24b53a35ecc (patch)
tree944f5483024f383a6207291ffdefd831a23f1c10
parent3ca56fe57785e4c4c7e76e58a6be982174ca7337 (diff)
downloadydb-f9a0c8229df295ad699d1395f7f5c24b53a35ecc.tar.gz
YQL-8971 YQL-15555 Fix unique in case inner + any join.
-rw-r--r--ydb/library/yql/core/yql_expr_constraint.cpp23
-rw-r--r--ydb/library/yql/core/yql_join.cpp32
-rw-r--r--ydb/library/yql/providers/dq/provider/yql_dq_datasink_constraints.cpp21
3 files changed, 44 insertions, 32 deletions
diff --git a/ydb/library/yql/core/yql_expr_constraint.cpp b/ydb/library/yql/core/yql_expr_constraint.cpp
index cacf929e975..48c8603f167 100644
--- a/ydb/library/yql/core/yql_expr_constraint.cpp
+++ b/ydb/library/yql/core/yql_expr_constraint.cpp
@@ -2534,7 +2534,6 @@ private:
const bool lOneRow = lUnique && lUnique->HasEqualColumns(GetKeys(core.LeftKeysColumns().Ref()));
const bool rOneRow = rUnique && rUnique->HasEqualColumns(GetKeys(core.RightKeysColumns().Ref()));
- const bool bothOne = lOneRow && rOneRow;
const bool singleSide = joinType.Content().ends_with("Semi") || joinType.Content().ends_with("Only");
@@ -2552,13 +2551,17 @@ private:
unique = lUnique->RenameFields(ctx, leftRename);
else if (rightSide && rUnique)
unique = rUnique->RenameFields(ctx, rightRename);
- } else if (joinType.IsAtom("Exclusion") || (lOneRow && rOneRow && joinType.IsAtom({"Inner", "Full", "Left", "Right"}))) {
- if (lUnique && rUnique)
- unique = TUniqueConstraintNode::Merge(lUnique->RenameFields(ctx, leftRename), rUnique->RenameFields(ctx, rightRename), ctx);
- else if (lUnique)
+ } else {
+ const bool exclusion = joinType.IsAtom("Exclusion");
+ const bool useLeft = lUnique && (rOneRow || exclusion);
+ const bool useRight = rUnique && (lOneRow || exclusion);
+
+ if (useLeft && !useRight)
unique = lUnique->RenameFields(ctx, leftRename);
- else if (rUnique)
- unique = rUnique->RenameFields(ctx, rightRename);
+ else if (useRight && !useLeft)
+ unique = lUnique->RenameFields(ctx, leftRename);
+ else if (useLeft && useRight)
+ unique = TUniqueConstraintNode::Merge(lUnique->RenameFields(ctx, leftRename), rUnique->RenameFields(ctx, rightRename), ctx);
}
const auto lDistinct = core.LeftInput().Ref().GetConstraint<TDistinctConstraintNode>();
@@ -2570,9 +2573,9 @@ private:
else if (rightSide && rDistinct)
distinct = rDistinct->RenameFields(ctx, rightRename);
} else {
- const bool useBoth = bothOne && joinType.IsAtom("Inner");
- const bool useLeft = lDistinct && ((leftSide && rOneRow) || useBoth);
- const bool useRight = rDistinct && ((rightSide && lOneRow) || useBoth);
+ const bool inner = joinType.IsAtom("Inner");
+ const bool useLeft = lDistinct && rOneRow && (inner || leftSide);
+ const bool useRight = rDistinct && lOneRow && (inner || rightSide);
if (useLeft && !useRight)
distinct = lDistinct->RenameFields(ctx, leftRename);
diff --git a/ydb/library/yql/core/yql_join.cpp b/ydb/library/yql/core/yql_join.cpp
index 1eba696aba5..109c7ec0c2b 100644
--- a/ydb/library/yql/core/yql_join.cpp
+++ b/ydb/library/yql/core/yql_join.cpp
@@ -259,7 +259,7 @@ namespace {
scope.clear();
- const bool singleSide = joinType.Content().ends_with("Only") || joinType.Content().ends_with("Semi");
+ const bool singleSide = joinType.Content().ends_with("Only") || joinType.Content().ends_with("Semi");
const bool rightSide = joinType.Content().starts_with("Right");
const bool leftSide = joinType.Content().starts_with("Left");
@@ -334,9 +334,11 @@ namespace {
}
}
- const bool lOneRow = (lUnique && lUnique->HasEqualColumns(lCheck)) || (leftHints && (leftHints->contains("unique") || leftHints->contains("any")));
- const bool rOneRow = (rUnique && rUnique->HasEqualColumns(rCheck)) || (rightHints && (rightHints->contains("unique") || rightHints->contains("any")));
- const bool bothOne = lOneRow && rOneRow;
+ const bool lAny = leftHints && (leftHints->contains("unique") || leftHints->contains("any"));
+ const bool rAny = rightHints && (rightHints->contains("unique") || rightHints->contains("any"));
+
+ const bool lOneRow = lAny || lUnique && lUnique->HasEqualColumns(lCheck);
+ const bool rOneRow = rAny || rUnique && rUnique->HasEqualColumns(rCheck);
if (unique) {
if (singleSide) {
@@ -344,13 +346,17 @@ namespace {
*unique = lUnique;
else if (rightSide)
*unique = rUnique;
- } else if (joinType.IsAtom("Exclusion") || (lOneRow && rOneRow && joinType.IsAtom({"Inner", "Full", "Left", "Right"}))) {
- if (lUnique && rUnique)
- *unique = TUniqueConstraintNode::Merge(lUnique, rUnique, ctx);
- else if (lUnique)
+ } else if (!joinType.IsAtom("Cross")) {
+ const bool exclusion = joinType.IsAtom("Exclusion") ;
+ const bool useLeft = lUnique && (rOneRow || exclusion);
+ const bool useRight = rUnique && (lOneRow || exclusion);
+
+ if (useLeft && !useRight)
*unique = lUnique;
- else if (rUnique)
+ else if (useRight && !useLeft)
*unique = rUnique;
+ else if (useLeft && useRight)
+ *unique = TUniqueConstraintNode::Merge(lUnique, rUnique, ctx);
}
}
@@ -360,10 +366,10 @@ namespace {
*distinct = lDistinct;
else if (rightSide)
*distinct = rDistinct;
- } else {
- const bool useBoth = bothOne && joinType.IsAtom("Inner");
- const bool useLeft = lDistinct && ((leftSide && rOneRow) || useBoth);
- const bool useRight = rDistinct && ((rightSide && lOneRow) || useBoth);
+ } else if (!joinType.IsAtom("Cross")) {
+ const bool inner = joinType.IsAtom("Inner");
+ const bool useLeft = lDistinct && rOneRow && (inner || leftSide);
+ const bool useRight = rDistinct && lOneRow && (inner || rightSide);
if (useLeft && !useRight)
*distinct = lDistinct;
diff --git a/ydb/library/yql/providers/dq/provider/yql_dq_datasink_constraints.cpp b/ydb/library/yql/providers/dq/provider/yql_dq_datasink_constraints.cpp
index f08ff6628b8..ceb82185f91 100644
--- a/ydb/library/yql/providers/dq/provider/yql_dq_datasink_constraints.cpp
+++ b/ydb/library/yql/providers/dq/provider/yql_dq_datasink_constraints.cpp
@@ -175,7 +175,6 @@ public:
const bool lOneRow = lUnique && lUnique->HasEqualColumns(leftJoinKeys);
const bool rOneRow = rUnique && rUnique->HasEqualColumns(rightJoinKeys);
- const bool bothOne = lOneRow && rOneRow;
const auto makeRename = [&ctx](const TExprBase& label) -> TConstraintNode::TPathReduce {
if (label.Ref().IsAtom()) {
@@ -199,13 +198,17 @@ public:
unique = leftRename ? lUnique->RenameFields(ctx, leftRename) : lUnique;
else if (rightSide && rUnique)
unique = rightRename ? rUnique->RenameFields(ctx, rightRename) : rUnique;
- } else if (joinType.IsAtom("Exclusion") || (lOneRow && rOneRow && joinType.IsAtom({"Inner", "Full", "Left", "Right"}))) {
- if (lUnique && rUnique)
- unique = TUniqueConstraintNode::Merge(leftRename ? lUnique->RenameFields(ctx, leftRename) : lUnique, rightRename ? rUnique->RenameFields(ctx, rightRename) : rUnique, ctx);
- else if (lUnique)
+ } else {
+ const bool exclusion = joinType.IsAtom("Exclusion");
+ const bool useLeft = lUnique && (rOneRow || exclusion);
+ const bool useRight = rUnique && (lOneRow || exclusion);
+
+ if (useLeft && !useRight)
unique = leftRename ? lUnique->RenameFields(ctx, leftRename) : lUnique;
- else if (rUnique)
+ else if (useRight && !useLeft)
unique = rightRename ? rUnique->RenameFields(ctx, rightRename) : rUnique;
+ else if (useRight && useLeft)
+ unique = TUniqueConstraintNode::Merge(leftRename ? lUnique->RenameFields(ctx, leftRename) : lUnique, rightRename ? rUnique->RenameFields(ctx, rightRename) : rUnique, ctx);
}
const auto lDistinct = join.LeftInput().Ref().GetConstraint<TDistinctConstraintNode>();
@@ -217,9 +220,9 @@ public:
else if (rightSide && rDistinct)
distinct = rightRename ? rDistinct->RenameFields(ctx, rightRename) : rDistinct;
} else {
- const bool useBoth = bothOne && joinType.IsAtom("Inner");
- const bool useLeft = lDistinct && ((leftSide && rOneRow) || useBoth);
- const bool useRight = rDistinct && ((rightSide && lOneRow) || useBoth);
+ const bool inner = joinType.IsAtom("Inner");
+ const bool useLeft = lDistinct && rOneRow && (inner || leftSide);
+ const bool useRight = rDistinct && lOneRow && (inner || rightSide);
if (useLeft && !useRight)
distinct = leftRename ? lDistinct->RenameFields(ctx, leftRename) : lDistinct;