8000 Merge branch 'selection_handler' into piggyback_master · mpws2013n1/postgres@9e1eaba · GitHub
[go: up one dir, main page]

Skip to content

Commit 9e1eaba

Browse files
committed
Merge branch 'selection_handler' into piggyback_master
2 parents a4d3726 + 31de00f commit 9e1eaba

File tree

1 file changed

+121
-21
lines changed

1 file changed

+121
-21
lines changed

src/backend/executor/execProcnode.c

Lines changed: 121 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,9 @@ void addToTwoColumnCombinationHashSet(int from, char* valueToConcat, int to, cha
132132
void LookForFilterWithEquality(PlanState* result, Oid tableOid, List* qual);
133133
void InvalidateStatisticsForTables(List* oldTableOids);
134134
void InvalidateStatisticsForTable(int tableOid);
135+
void SetStatisticValuesForEqual(int* equationValue, int columnStatisticId, be_PGAttDesc *columnData);
136+
void SetStatisticValuesForUnequal(bool greaterThan, bool orEquals,int* equationValue, int columnStatisticId, be_PGAttDesc *columnData);
137+
135138
/* ------------------------------------------------------------------------
136139
* ExecInitNode
137140
*
@@ -448,6 +451,76 @@ InvalidateStatisticsForTable(int tableOid)
448451
}
449452
}
450453

454+
void
455+
SetStatisticValuesForEqual(int* equationValue, int columnStatisticId, be_PGAttDesc *columnData) {
456+
// only write values, if the selected field is part of the result table
457+
if (columnStatisticId < piggyback->numberOfAttributes){
458+
piggyback->resultStatistics->columnStatistics[columnStatisticId].columnDescriptor = columnData;
459+
piggyback->resultStatistics->columnStatistics[columnStatisticId].isNumeric = 1;
460+
piggyback->resultStatistics->columnStatistics[columnStatisticId].maxValue = equationValue;
461+
piggyback->resultStatistics->columnStatistics[columnStatisticId].minValue = equationValue;
462+
piggyback->resultStatistics->columnStatistics[columnStatisticId].mostFrequentValue = equationValue;
463+
piggyback->resultStatistics->columnStatistics[columnStatisticId].n_distinct = 1;
464+
465+
// the meta data for this column is complete and should not be calculated again
466+
piggyback->resultStatistics->columnStatistics[columnStatisticId].n_distinctIsFinal = 1;
467+
piggyback->resultStatistics->columnStatistics[columnStatisticId].minValueIsFinal = 1;
468+
piggyback->resultStatistics->columnStatistics[columnStatisticId].maxValueIsFinal = 1;
469+
piggyback->resultStatistics->columnStatistics[columnStatisticId].mostFrequentValueIsFinal = 1;
470+
}
471+
else {
472+
printf("there are statistics results from a selection with = that are not part of the result table\n");
473+
}
474+
}
475+
476+
// meaning of the first and second parameter:
477+
// >= == greaterThan true, orEquals true
478+
// > == greaterThan true, orEquals false
479+
// <= == greaterThan false, orEquals true
480+
// < == greaterThan false, orEquals false
481+
void
482+
SetStatisticValuesForUnequal(bool greaterThan, bool orEquals, int* equationValue, int columnStatisticId, be_PGAttDesc *columnData) {
483+
// only write values, if the selected field is part of the result table
484+
int *value = (int*) malloc(sizeof(int));
485+
if (!orEquals)
486+
{
487+
if (greaterThan) // for instance x > 3 means x has at least the value 4
488+
{
489+
*value = *equationValue + 1;
490+
}
491+
else // for instance x < 3 means x has at maximum the value 2
492+
{
493+
*value = *equationValue - 1;
494+
}
495+
}
496+
else
497+
{
498+
*value = *equationValue;
499+
}
500+
501+
if (columnStatisticId < piggyback->numberOfAttributes)
502+
{
503+
piggyback->resultStatistics->columnStatistics[columnStatisticId].columnDescriptor = columnData;
504+
if(greaterThan)
505+
piggyback->resultStatistics->columnStatistics[columnStatisticId].minValue = value;
506+
else
507+
piggyback->resultStatistics->columnStatistics[columnStatisticId].maxValue = value;
508+
509+
// the meta data for this column is complete and should not be calculated again
510+
if(greaterThan)
511+
piggyback->resultStatistics->columnStatistics[columnStatisticId].minValueIsFinal = 1;
512+
else
513+
piggyback->resultStatistics->columnStatistics[columnStatisticId].maxValueIsFinal = 1;
514+
515+
piggyback->resultStatistics->columnStatistics[columnStatisticId].n_distinctIsFinal = 0;
516+
piggyback->resultStatistics->columnStatistics[columnStatisticId].mostFrequentValueIsFinal = 0;
517+
}
518+
else
519+
{
520+
printf("there are statistics results from a selection with > or < with a constant that are not part of the result table\n");
521+
}
522+
}
523+
451524
void
452525
LookForFilterWithEquality(PlanState* result, Oid tableOid, List* qual)
453526
{
@@ -466,6 +539,8 @@ LookForFilterWithEquality(PlanState* result, Oid tableOid, List* qual)
466539
break;
467540
}
468541

542+
// the magic numbers are operator identifiers from posgres/src/include/catalog/pg_operator.h
543+
// equals
469544
if(opno == 94 || opno == 96 || opno == 410 || opno == 416 || opno == 1862 || opno == 1868 || opno == 15 || opno == 532 || opno == 533) { // it is a equality like number_of_tracks = 3
470545
int numberOfAttributes = result->plan->targetlist->length;
471546

@@ -475,29 +550,54 @@ LookForFilterWithEquality(PlanState* result, Oid tableOid, List* qual)
475550
// we always set the type to 8byte-integer because we don't need a detailed differentiation
476551
columnData->typid = 20;
477552

478-
// only write values, if the selected field is part of the result table
479-
if (i < piggyback->numberOfAttributes)
480-
{
481-
piggyback->resultStatistics->columnStatistics[i].columnDescriptor = columnData;
482-
piggyback->resultStatistics->columnStatistics[i].isNumeric = 1;
483-
piggyback->resultStatistics->columnStatistics[i].maxValue = minAndMaxAndAvg;
484-
piggyback->resultStatistics->columnStatistics[i].minValue = minAndMaxAndAvg;
485-
piggyback->resultStatistics->columnStatistics[i].mostFrequentValue = minAndMaxAndAvg;
486-
piggyback->resultStatistics->columnStatistics[i].n_distinct = 1;
487-
488-
// the meta data for this column is complete and should not be calculated again
489-
piggyback->resultStatistics->columnStatistics[i].n_distinctIsFinal = 1;
490-
piggyback->resultStatistics->columnStatistics[i].minValueIsFinal = 1;
491-
piggyback->resultStatistics->columnStatistics[i].maxValueIsFinal = 1;
492-
piggyback->resultStatistics->columnStatistics[i].mostFrequentValueIsFinal = 1;
493-
}
494-
else
495-
{
496-
printf("there are statistics results from the selection that are not part of the result table\n");
497-
}
553+
SetStatisticValuesForEqual(minAndMaxAndAvg, i, columnData);
554+
}
555+
// <
556+
else if(opno == 37 || opno == 95 || opno == 97 || opno == 412 || opno == 418 || opno == 534 || opno == 535 || opno == 1864 || opno == 1870) {
557+
558+
int *min = (int*) malloc(sizeof(int));
559+
min = &(((Const*) ((OpExpr*) ((ExprState*) linitial(qual))->expr)->args->tail->data.ptr_value)->constvalue);
560+
561+
// we always set the type to 8byte-integer because we don't need a detailed differentiation
562+
columnData->typid = 20;
563+
564+
SetStatisticValuesForUnequal(false, false, min, i, columnData);
565+
}
566+
// <=
567+
else if(opno == 80 || opno == 414 || opno == 420 || opno == 522 || opno == 523 || opno == 540 || opno == 541 || opno == 1866 || opno == 1872) {
568+
569+
int *min = (int*) malloc(sizeof(int));
570+
min = &(((Const*) ((OpExpr*) ((ExprState*) linitial(qual))->expr)->args->tail->data.ptr_value)->constvalue);
571+
572+
// we always set the type to 8byte-integer because we don't need a detailed differentiation
573+
columnData->typid = 20;
574+
575+
SetStatisticValuesForUnequal(false, true, min, i, columnData);
576+
}
577+
// >
578+
else if(opno == 76 || opno == 413 || opno == 419 || opno == 520 || opno == 521 || opno == 536 || opno == 1865 || opno == 1871) {
579+
580+
int *max = (int*) malloc(sizeof(int));
581+
max = &(((Const*) ((OpExpr*) ((ExprState*) linitial(qual))->expr)->args->tail->data.ptr_value)->constvalue);
582+
583+
// we always set the type to 8byte-integer because we don't need a detailed differentiation
584+
columnData->typid = 20;
585+
586+
SetStatisticValuesForUnequal(true, false, max, i, columnData);
587+
}
588+
// >=
589+
else if(opno == 82 || opno == 415 || opno == 430 || opno == 524 || opno == 525 || opno == 537 || opno == 542 || opno == 543 || opno == 1867 || opno == 1873) {
590+
591+
int *max = (int*) malloc(sizeof(int));
592+
max = &(((Const*) ((OpExpr*) ((ExprState*) linitial(qual))->expr)->args->tail->data.ptr_value)->constvalue);
593+
594+
// we always set the type to 8byte-integer because we don't need a detailed differentiation
595+
columnData->typid = 20;
596+
597+
SetStatisticValuesForUnequal(true, true, max, i, columnData);
498598
}
499599
else {
500-
printf("this opno is no equality: %d (for column id %d)\n", opno, columnId);
600+
printf("this opno is no =, <, >, <= or >=: %d (for column id %d)\n", opno, columnId);
501601
// found a selection, therefore we cannot use old statistics
502602
InvalidateStatisticsForTable(tableOid);
503603
}

0 commit comments

Comments
 (0)
0