Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit370d6cd

Browse files
committed
From: David Hartwig <daybee@bellatlantic.net>I put some extra checks to make sure a query was a good candidate forrewrite into a UNION. Besides the existing checks:1. Make sure the AND/OR tree was rectangular. ( i.e. 3 X 4 or 10 X3)2. Only one table.3. Must have an AND dimension.4. At least 9 OP expressions totalAlso cleaned up and commented.
1 parente9d0fa3 commit370d6cd

File tree

1 file changed

+55
-55
lines changed

1 file changed

+55
-55
lines changed

‎src/backend/optimizer/prep/prepkeyset.c

Lines changed: 55 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -11,35 +11,20 @@
1111
#include<string.h>
1212

1313
#include"postgres.h"
14-
#include"nodes/pg_list.h"
15-
#include"nodes/parsenodes.h"
16-
#include"utils/elog.h"
17-
18-
#include"nodes/nodes.h"
19-
#include"nodes/execnodes.h"
20-
#include"nodes/plannodes.h"
21-
#include"nodes/primnodes.h"
22-
#include"nodes/relation.h"
23-
24-
#include"catalog/pg_type.h"
25-
#include"lib/stringinfo.h"
2614
#include"optimizer/planmain.h"
15+
2716
/*
2817
* Node_Copy--
2918
* a macro to simplify calling of copyObject on the specified field
3019
*/
3120
#defineNode_Copy(from,newnode,field) newnode->field = copyObject(from->field)
3221

33-
/***** DEBUG stuff
34-
#define TABS {int i; printf("\n"); for (i = 0; i<level; i++) printf("\t"); }
35-
static int level = 0;
36-
******/
37-
3822
bool_use_keyset_query_optimizer= FALSE;
3923

4024
staticintinspectOpNode(Expr*expr);
4125
staticintinspectAndNode(Expr*expr);
4226
staticintinspectOrNode(Expr*expr);
27+
staticintTotalExpr;
4328

4429
/**********************************************************************
4530
* This routine transforms query trees with the following form:
@@ -73,8 +58,7 @@ static int inspectOrNode(Expr *expr);
7358
*
7459
* daveh@insightdist.com 1998-08-31
7560
*
76-
* Needs to better identify the signeture WHERE clause.
77-
* May want to also prune out duplicate where clauses.
61+
* May want to also prune out duplicate terms.
7862
**********************************************************************/
7963
void
8064
transformKeySetQuery(Query*origNode)
@@ -92,18 +76,20 @@ transformKeySetQuery(Query *origNode)
9276
return;
9377

9478
/* Qualify single table query */
95-
79+
if (length(origNode->rtable)!=1)
80+
return;
81+
82+
/* Sorry about the global, not worth passing around */
83+
/* 9 expressions seems like a good number. More than 9 */
84+
/* and it starts to slow down quite a bit */
85+
TotalExpr=0;
86+
/*************************/
9687
/* Qualify where clause */
97-
if ( !inspectOrNode((Expr*)origNode->qual)) {
88+
/*************************/
89+
if ( !inspectOrNode((Expr*)origNode->qual)||TotalExpr<9)
9890
return;
99-
}
10091

10192
/* Copy essential elements into a union node */
102-
/*
103-
elog(NOTICE, "OR_EXPR=%d, OP_EXPR=%d, AND_EXPR=%d", OR_EXPR, OP_EXPR, AND_EXPR);
104-
elog(NOTICE, "T_List=%d, T_Expr=%d, T_Var=%d, T_Const=%d", T_List, T_Expr, T_Var, T_Const);
105-
elog(NOTICE, "opType=%d", ((Expr*)origNode->qual)->opType);
106-
*/
10793
while (((Expr*)origNode->qual)->opType==OR_EXPR) {
10894
Query*unionNode=makeNode(Query);
10995

@@ -113,11 +99,6 @@ transformKeySetQuery(Query *origNode)
11399
/* Pull up balance of tree */
114100
origNode->qual=lfirst(((Expr*)origNode->qual)->args);
115101

116-
/*
117-
elog(NOTICE, "origNode: opType=%d, nodeTag=%d", ((Expr*)origNode->qual)->opType, nodeTag(origNode->qual));
118-
elog(NOTICE, "unionNode: opType=%d, nodeTag=%d", ((Expr*)unionNode->qual)->opType, nodeTag(unionNode->qual));
119-
*/
120-
121102
unionNode->commandType=origNode->commandType;
122103
unionNode->resultRelation=origNode->resultRelation;
123104
unionNode->isPortal=origNode->isPortal;
@@ -139,9 +120,14 @@ transformKeySetQuery(Query *origNode)
139120

140121

141122
staticint
123+
/**********************************************************************
124+
* Checks for 1 or more OR terms w/ 1 or more AND terms.
125+
* AND terms must be equal in size.
126+
* Returns the number of each AND term.
127+
**********************************************************************/
142128
inspectOrNode(Expr*expr)
143129
{
144-
intfr=0,sr=0;
130+
intrc;
145131
Expr*firstExpr,*secondExpr;
146132

147133
if ( ! (expr&&nodeTag(expr)==T_Expr&&expr->opType==OR_EXPR))
@@ -152,27 +138,35 @@ inspectOrNode(Expr *expr)
152138
if (nodeTag(firstExpr)!=T_Expr||nodeTag(secondExpr)!=T_Expr)
153139
return0;
154140

155-
if (firstExpr->opType==OR_EXPR)
156-
fr=inspectOrNode(firstExpr);
157-
elseif (firstExpr->opType==OP_EXPR)/* Need to make sure it is last */
158-
fr=inspectOpNode(firstExpr);
159-
elseif (firstExpr->opType==AND_EXPR)/* Need to make sure it is last */
160-
fr=inspectAndNode(firstExpr);
161-
141+
if (firstExpr->opType==OR_EXPR&&secondExpr->opType==AND_EXPR)
142+
{
143+
if ((rc=inspectOrNode(firstExpr))==0)
144+
return0;
162145

163-
if (secondExpr->opType==AND_EXPR)
164-
sr=inspectAndNode(secondExpr);
165-
elseif (secondExpr->opType==OP_EXPR)
166-
sr=inspectOpNode(secondExpr);
146+
return (rc==inspectAndNode(secondExpr)) ?rc :0;
147+
}
148+
elseif (firstExpr->opType==AND_EXPR&&secondExpr->opType==AND_EXPR)
149+
{
150+
if ((rc=inspectAndNode(firstExpr))==0)
151+
return0;
152+
153+
return (rc==inspectAndNode(secondExpr)) ?rc :0;
167154

168-
return (fr&&sr);
155+
}
156+
157+
return0;
169158
}
170159

171160

172161
staticint
162+
/**********************************************************************
163+
* Check for one or more AND terms. Each sub-term must be a T_Const
164+
* T_Var expression.
165+
* Returns the number of AND terms.
166+
**********************************************************************/
173167
inspectAndNode(Expr*expr)
174168
{
175-
intfr=0,sr=0;
169+
intrc;
176170
Expr*firstExpr,*secondExpr;
177171

178172
if ( ! (expr&&nodeTag(expr)==T_Expr&&expr->opType==AND_EXPR))
@@ -183,15 +177,19 @@ inspectAndNode(Expr *expr)
183177
if (nodeTag(firstExpr)!=T_Expr||nodeTag(secondExpr)!=T_Expr)
184178
return0;
185179

186-
if (firstExpr->opType==AND_EXPR)
187-
fr=inspectAndNode(firstExpr);
188-
elseif (firstExpr->opType==OP_EXPR)
189-
fr=inspectOpNode(firstExpr);
180+
if (firstExpr->opType==AND_EXPR&&
181+
secondExpr->opType==OP_EXPR&&inspectOpNode(secondExpr))
182+
{
183+
rc=inspectAndNode(firstExpr);
184+
return ((rc) ? (rc+1) :0);/* Add up the AND nodes */
185+
}
186+
elseif (firstExpr->opType==OP_EXPR&&inspectOpNode(firstExpr)&&
187+
secondExpr->opType==OP_EXPR&&inspectOpNode(secondExpr))
188+
{
189+
return1;
190+
}
190191

191-
if (secondExpr->opType==OP_EXPR)
192-
sr=inspectOpNode(secondExpr);
193-
194-
return (fr&&sr);
192+
return0;
195193
}
196194

197195

@@ -205,7 +203,9 @@ inspectOpNode(Expr *expr)
205203
Expr*firstExpr,*secondExpr;
206204

207205
if (nodeTag(expr)!=T_Expr||expr->opType!=OP_EXPR)
208-
return0;
206+
return FALSE;
207+
208+
TotalExpr++;
209209

210210
firstExpr=lfirst(expr->args);
211211
secondExpr=lsecond(expr->args);

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp