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

Commit422221c

Browse files
committed
Another SELECT speedup: extract OIDs of column print functions
only once per SELECT, not once per tuple. 10% here, 10% there,pretty soon you're talking about real speedups ...
1 parent36693c0 commit422221c

File tree

9 files changed

+390
-208
lines changed

9 files changed

+390
-208
lines changed

‎src/backend/access/common/printtup.c

Lines changed: 109 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*
99
*
1010
* IDENTIFICATION
11-
* $Header: /cvsroot/pgsql/src/backend/access/common/printtup.c,v 1.39 1999/01/24 22:50:58 tgl Exp $
11+
* $Header: /cvsroot/pgsql/src/backend/access/common/printtup.c,v 1.40 1999/01/27 00:36:22 tgl Exp $
1212
*
1313
*-------------------------------------------------------------------------
1414
*/
@@ -27,6 +27,10 @@
2727
#include<mb/pg_wchar.h>
2828
#endif
2929

30+
staticvoidprinttup_setup(DestReceiver*self,TupleDesctypeinfo);
31+
staticvoidprinttup(HeapTupletuple,TupleDesctypeinfo,DestReceiver*self);
32+
staticvoidprinttup_cleanup(DestReceiver*self);
33+
3034
/* ----------------------------------------------------------------
3135
*printtup / debugtup support
3236
* ----------------------------------------------------------------
@@ -64,26 +68,105 @@ getTypeOutAndElem(Oid type, Oid* typOutput, Oid* typElem)
6468
return0;
6569
}
6670

71+
/* ----------------
72+
*Private state for a printtup destination object
73+
* ----------------
74+
*/
75+
typedefstruct {/* Per-attribute information */
76+
Oidtypoutput;/* Oid for the attribute's type output fn */
77+
Oidtypelem;/* typelem value to pass to the output fn */
78+
/* more soon... */
79+
}PrinttupAttrInfo;
80+
81+
typedefstruct {
82+
DestReceiverpub;/* publicly-known function pointers */
83+
TupleDescattrinfo;/* The attr info we are set up for */
84+
intnattrs;
85+
PrinttupAttrInfo*myinfo;/* Cached info about each attr */
86+
}DR_printtup;
87+
88+
/* ----------------
89+
*Initialize: create a DestReceiver for printtup
90+
* ----------------
91+
*/
92+
DestReceiver*
93+
printtup_create_DR()
94+
{
95+
DR_printtup*self= (DR_printtup*)palloc(sizeof(DR_printtup));
96+
97+
self->pub.receiveTuple=printtup;
98+
self->pub.setup=printtup_setup;
99+
self->pub.cleanup=printtup_cleanup;
100+
101+
self->attrinfo=NULL;
102+
self->nattrs=0;
103+
self->myinfo=NULL;
104+
105+
return (DestReceiver*)self;
106+
}
107+
108+
staticvoid
109+
printtup_setup(DestReceiver*self,TupleDesctypeinfo)
110+
{
111+
/* ----------------
112+
* We could set up the derived attr info at this time, but we postpone it
113+
* until the first call of printtup, for 3 reasons:
114+
* 1. We don't waste time (compared to the old way) if there are no
115+
* tuples at all to output.
116+
* 2. Checking in printtup allows us to handle the case that the tuples
117+
* change type midway through (although this probably can't happen in
118+
* the current executor).
119+
* 3. Right now, ExecutorRun passes a NULL for typeinfo anyway :-(
120+
* ----------------
121+
*/
122+
}
123+
124+
staticvoid
125+
printtup_prepare_info(DR_printtup*myState,TupleDesctypeinfo,intnumAttrs)
126+
{
127+
inti;
128+
129+
if (myState->myinfo)
130+
pfree(myState->myinfo);/* get rid of any old data */
131+
myState->myinfo=NULL;
132+
myState->attrinfo=typeinfo;
133+
myState->nattrs=numAttrs;
134+
if (numAttrs <=0)
135+
return;
136+
myState->myinfo= (PrinttupAttrInfo*)
137+
palloc(numAttrs*sizeof(PrinttupAttrInfo));
138+
for (i=0;i<numAttrs;i++)
139+
{
140+
PrinttupAttrInfo*thisState=myState->myinfo+i;
141+
getTypeOutAndElem((Oid)typeinfo->attrs[i]->atttypid,
142+
&thisState->typoutput,&thisState->typelem);
143+
}
144+
}
145+
67146
/* ----------------
68147
*printtup
69148
* ----------------
70149
*/
71-
void
72-
printtup(HeapTupletuple,TupleDesctypeinfo)
150+
staticvoid
151+
printtup(HeapTupletuple,TupleDesctypeinfo,DestReceiver*self)
73152
{
153+
DR_printtup*myState= (DR_printtup*)self;
74154
inti,
75155
j,
76156
k,
77157
outputlen;
78158
char*outputstr;
79159
Datumattr;
80160
boolisnull;
81-
Oidtypoutput,
82-
typelem;
83161
#ifdefMULTIBYTE
84162
unsignedchar*p;
85163
#endif
86164

165+
/* Set or update my derived attribute info, if needed */
166+
if (myState->attrinfo!=typeinfo||
167+
myState->nattrs!=tuple->t_data->t_natts)
168+
printtup_prepare_info(myState,typeinfo,tuple->t_data->t_natts);
169+
87170
/* ----------------
88171
*tell the frontend to expect new tuple data (in ASCII style)
89172
* ----------------
@@ -120,10 +203,11 @@ printtup(HeapTuple tuple, TupleDesc typeinfo)
120203
attr=heap_getattr(tuple,i+1,typeinfo,&isnull);
121204
if (isnull)
122205
continue;
123-
if (getTypeOutAndElem((Oid)typeinfo->attrs[i]->atttypid,
124-
&typoutput,&typelem))
206+
if (OidIsValid(myState->myinfo[i].typoutput))
125207
{
126-
outputstr=fmgr(typoutput,attr,typelem,
208+
outputstr=fmgr(myState->myinfo[i].typoutput,
209+
attr,
210+
myState->myinfo[i].typelem,
127211
typeinfo->attrs[i]->atttypmod);
128212
#ifdefMULTIBYTE
129213
p=pg_server_to_client(outputstr,strlen(outputstr));
@@ -147,6 +231,19 @@ printtup(HeapTuple tuple, TupleDesc typeinfo)
147231
}
148232
}
149233

234+
/* ----------------
235+
*printtup_cleanup
236+
* ----------------
237+
*/
238+
staticvoid
239+
printtup_cleanup(DestReceiver*self)
240+
{
241+
DR_printtup*myState= (DR_printtup*)self;
242+
if (myState->myinfo)
243+
pfree(myState->myinfo);
244+
pfree(myState);
245+
}
246+
150247
/* ----------------
151248
*printatt
152249
* ----------------
@@ -190,7 +287,7 @@ showatts(char *name, TupleDesc tupleDesc)
190287
* ----------------
191288
*/
192289
void
193-
debugtup(HeapTupletuple,TupleDesctypeinfo)
290+
debugtup(HeapTupletuple,TupleDesctypeinfo,DestReceiver*self)
194291
{
195292
inti;
196293
Datumattr;
@@ -221,11 +318,12 @@ debugtup(HeapTuple tuple, TupleDesc typeinfo)
221318
*We use a different data prefix, e.g. 'B' instead of 'D' to
222319
*indicate a tuple in internal (binary) form.
223320
*
224-
*This is same as printtup, except we don't use the typout func.
321+
*This is same as printtup, except we don't use the typout func,
322+
*and therefore have no need for persistent state.
225323
* ----------------
226324
*/
227325
void
228-
printtup_internal(HeapTupletuple,TupleDesctypeinfo)
326+
printtup_internal(HeapTupletuple,TupleDesctypeinfo,DestReceiver*self)
229327
{
230328
inti,
231329
j,

‎src/backend/executor/execMain.c

Lines changed: 26 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@
2626
*
2727
*
2828
* IDENTIFICATION
29-
* $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.63 1999/01/25 12:01:03 vadim Exp $
29+
* $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.64 1999/01/27 00:36:20 tgl Exp $
3030
*
3131
*-------------------------------------------------------------------------
3232
*/
@@ -66,9 +66,10 @@ static void EndPlan(Plan *plan, EState *estate);
6666
staticTupleTableSlot*ExecutePlan(EState*estate,Plan*plan,
6767
Query*parseTree,CmdTypeoperation,
6868
intnumberTuples,ScanDirectiondirection,
69-
void (*printfunc) ());
70-
staticvoidExecRetrieve(TupleTableSlot*slot,void (*printfunc) (),
71-
EState*estate);
69+
DestReceiver*destfunc);
70+
staticvoidExecRetrieve(TupleTableSlot*slot,
71+
DestReceiver*destfunc,
72+
EState*estate);
7273
staticvoidExecAppend(TupleTableSlot*slot,ItemPointertupleid,
7374
EState*estate);
7475
staticvoidExecDelete(TupleTableSlot*slot,ItemPointertupleid,
@@ -171,7 +172,7 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
171172
Plan*plan;
172173
TupleTableSlot*result;
173174
CommandDestdest;
174-
void(*destination) ();
175+
DestReceiver*destfunc;
175176

176177
/******************
177178
*sanity checks
@@ -188,10 +189,19 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
188189
parseTree=queryDesc->parsetree;
189190
plan=queryDesc->plantree;
190191
dest=queryDesc->dest;
191-
destination= (void (*) ())DestToFunction(dest);
192+
destfunc=DestToFunction(dest);
192193
estate->es_processed=0;
193194
estate->es_lastoid=InvalidOid;
194195

196+
/******************
197+
*FIXME: the dest setup function ought to be handed the tuple desc
198+
* for the tuples to be output, but I'm not quite sure how to get that
199+
* info at this point. For now, passing NULL is OK because no existing
200+
* dest setup function actually uses the pointer.
201+
******************
202+
*/
203+
(*destfunc->setup) (destfunc, (TupleDesc)NULL);
204+
195205
switch (feature)
196206
{
197207

@@ -202,7 +212,7 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
202212
operation,
203213
ALL_TUPLES,
204214
ForwardScanDirection,
205-
destination);
215+
destfunc);
206216
break;
207217
caseEXEC_FOR:
208218
result=ExecutePlan(estate,
@@ -211,7 +221,7 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
211221
operation,
212222
count,
213223
ForwardScanDirection,
214-
destination);
224+
destfunc);
215225
break;
216226

217227
/******************
@@ -225,7 +235,7 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
225235
operation,
226236
count,
227237
BackwardScanDirection,
228-
destination);
238+
destfunc);
229239
break;
230240

231241
/******************
@@ -240,14 +250,16 @@ ExecutorRun(QueryDesc *queryDesc, EState *estate, int feature, int count)
240250
operation,
241251
ONE_TUPLE,
242252
ForwardScanDirection,
243-
destination);
253+
destfunc);
244254
break;
245255
default:
246256
result=NULL;
247257
elog(DEBUG,"ExecutorRun: Unknown feature %d",feature);
248258
break;
249259
}
250260

261+
(*destfunc->cleanup) (destfunc);
262+
251263
returnresult;
252264
}
253265

@@ -745,7 +757,7 @@ ExecutePlan(EState *estate,
745757
CmdTypeoperation,
746758
intnumberTuples,
747759
ScanDirectiondirection,
748-
void (*printfunc) ())
760+
DestReceiver*destfunc)
749761
{
750762
JunkFilter*junkfilter;
751763

@@ -905,7 +917,7 @@ ExecutePlan(EState *estate,
905917
{
906918
caseCMD_SELECT:
907919
ExecRetrieve(slot,/* slot containing tuple */
908-
printfunc,/*print function */
920+
destfunc,/*destination's tuple-receiver obj */
909921
estate);/* */
910922
result=slot;
911923
break;
@@ -961,7 +973,7 @@ ExecutePlan(EState *estate,
961973
*/
962974
staticvoid
963975
ExecRetrieve(TupleTableSlot*slot,
964-
void (*printfunc) (),
976+
DestReceiver*destfunc,
965977
EState*estate)
966978
{
967979
HeapTupletuple;
@@ -988,7 +1000,7 @@ ExecRetrieve(TupleTableSlot *slot,
9881000
*send the tuple to the front end (or the screen)
9891001
******************
9901002
*/
991-
(*printfunc) (tuple,attrtype);
1003+
(*destfunc->receiveTuple) (tuple,attrtype,destfunc);
9921004
IncrRetrieved();
9931005
(estate->es_processed)++;
9941006
}

‎src/backend/executor/spi.c

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
* spi.c--
44
*Server Programming Interface
55
*
6-
* $Id: spi.c,v 1.30 1999/01/24 05:40:48 tgl Exp $
6+
* $Id: spi.c,v 1.31 1999/01/27 00:36:21 tgl Exp $
77
*
88
*-------------------------------------------------------------------------
99
*/
@@ -32,8 +32,6 @@ uint32SPI_processed = 0;
3232
SPITupleTable*SPI_tuptable;
3333
intSPI_result;
3434

35-
voidspi_printtup(HeapTupletuple,TupleDesctupdesc);
36-
3735
typedefstruct
3836
{
3937
QueryTreeList*qtlist;
@@ -566,7 +564,7 @@ SPI_pfree(void *pointer)
566564
*
567565
*/
568566
void
569-
spi_printtup(HeapTupletuple,TupleDesctupdesc)
567+
spi_printtup(HeapTupletuple,TupleDesctupdesc,DestReceiver*self)
570568
{
571569
SPITupleTable*tuptable;
572570
MemoryContextoldcxt;

‎src/backend/libpq/be-dumpdata.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
*
77
* Copyright (c) 1994, Regents of the University of California
88
*
9-
* $Id: be-dumpdata.c,v 1.20 1999/01/24 05:40:49 tgl Exp $
9+
* $Id: be-dumpdata.c,v 1.21 1999/01/27 00:36:12 tgl Exp $
1010
*
1111
*-------------------------------------------------------------------------
1212
*/
@@ -208,7 +208,7 @@ be_typeinit(PortalEntry *entry,
208208
* ----------------
209209
*/
210210
void
211-
be_printtup(HeapTupletuple,TupleDesctypeinfo)
211+
be_printtup(HeapTupletuple,TupleDesctypeinfo,DestReceiver*self)
212212
{
213213
inti;
214214
Datumattr;

‎src/backend/nodes/print.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
*
88
*
99
* IDENTIFICATION
10-
* $Header: /cvsroot/pgsql/src/backend/nodes/print.c,v 1.18 1998/09/01 04:29:10 momjian Exp $
10+
* $Header: /cvsroot/pgsql/src/backend/nodes/print.c,v 1.19 1999/01/27 00:36:28 tgl Exp $
1111
*
1212
* HISTORY
1313
* AUTHORDATEMAJOR EVENT
@@ -275,7 +275,7 @@ print_slot(TupleTableSlot *slot)
275275
return;
276276
}
277277

278-
debugtup(slot->val,slot->ttc_tupleDescriptor);
278+
debugtup(slot->val,slot->ttc_tupleDescriptor,NULL);
279279
}
280280

281281
staticchar*

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp