|
10 | 10 | * Portions Copyright (c) 1994, Regents of the University of California
|
11 | 11 | *
|
12 | 12 | * IDENTIFICATION
|
13 |
| - *$PostgreSQL: pgsql/src/backend/access/gist/gistproc.c,v 1.10 2007/01/05 22:19:22 momjian Exp $ |
| 13 | + *$PostgreSQL: pgsql/src/backend/access/gist/gistproc.c,v 1.11 2007/09/07 17:04:26 teodor Exp $ |
14 | 14 | *
|
15 | 15 | *-------------------------------------------------------------------------
|
16 | 16 | */
|
|
21 | 21 | #include"utils/geo_decls.h"
|
22 | 22 |
|
23 | 23 |
|
24 |
| -typedefstruct |
25 |
| -{ |
26 |
| -BOX*key; |
27 |
| -intpos; |
28 |
| -}KBsort; |
29 |
| - |
30 |
| -staticintcompare_KB(constvoid*a,constvoid*b); |
31 | 24 | staticboolgist_box_leaf_consistent(BOX*key,BOX*query,
|
32 | 25 | StrategyNumberstrategy);
|
33 | 26 | staticdoublesize_box(Datumdbox);
|
@@ -194,22 +187,6 @@ gist_box_penalty(PG_FUNCTION_ARGS)
|
194 | 187 | PG_RETURN_POINTER(result);
|
195 | 188 | }
|
196 | 189 |
|
197 |
| -/* |
198 |
| - * qsort comparator for box areas |
199 |
| - */ |
200 |
| -staticint |
201 |
| -compare_KB(constvoid*a,constvoid*b) |
202 |
| -{ |
203 |
| -BOX*abox= ((constKBsort*)a)->key; |
204 |
| -BOX*bbox= ((constKBsort*)b)->key; |
205 |
| -doublesa= (abox->high.x-abox->low.x)* (abox->high.y-abox->low.y); |
206 |
| -doublesb= (bbox->high.x-bbox->low.x)* (bbox->high.y-bbox->low.y); |
207 |
| - |
208 |
| -if (sa==sb) |
209 |
| -return0; |
210 |
| -return (sa>sb) ?1 :-1; |
211 |
| -} |
212 |
| - |
213 | 190 | staticvoid
|
214 | 191 | chooseLR(GIST_SPLITVEC*v,
|
215 | 192 | OffsetNumber*list1,intnlist1,BOX*union1,
|
@@ -417,44 +394,56 @@ gist_box_picksplit(PG_FUNCTION_ARGS)
|
417 | 394 | ADDLIST(listT,unionT,posT,i);
|
418 | 395 | }
|
419 | 396 |
|
420 |
| -/* bad disposition, sort by ascending and resplit */ |
421 |
| -if ((posR==0||posL==0)&& (posT==0||posB==0)) |
| 397 | +#defineLIMIT_RATIO0.1 |
| 398 | +#define_IS_BADRATIO(x,y)( (y) == 0 || (float)(x)/(float)(y) < LIMIT_RATIO ) |
| 399 | +#defineIS_BADRATIO(x,y) ( _IS_BADRATIO((x),(y)) || _IS_BADRATIO((y),(x)) ) |
| 400 | +/* bad disposition, try to split by centers of boxes */ |
| 401 | +if (IS_BADRATIO(posR,posL)&&IS_BADRATIO(posT,posB) ) |
422 | 402 | {
|
423 |
| -KBsort*arr= (KBsort*)palloc(sizeof(KBsort)*maxoff); |
| 403 | +doubleavgCenterX=0.0,avgCenterY=0.0; |
| 404 | +doubleCenterX,CenterY; |
424 | 405 |
|
425 |
| -posL=posR=posB=posT=0; |
426 | 406 | for (i=FirstOffsetNumber;i <=maxoff;i=OffsetNumberNext(i))
|
427 | 407 | {
|
428 |
| -arr[i-1].key=DatumGetBoxP(entryvec->vector[i].key); |
429 |
| -arr[i-1].pos=i; |
| 408 | +cur=DatumGetBoxP(entryvec->vector[i].key); |
| 409 | +avgCenterX+= ((double)cur->high.x+ (double)cur->low.x)/2.0; |
| 410 | +avgCenterY+= ((double)cur->high.y+ (double)cur->low.y)/2.0; |
430 | 411 | }
|
431 |
| -qsort(arr,maxoff,sizeof(KBsort),compare_KB); |
| 412 | + |
| 413 | +avgCenterX /=maxoff; |
| 414 | +avgCenterY /=maxoff; |
| 415 | + |
| 416 | +posL=posR=posB=posT=0; |
432 | 417 | for (i=FirstOffsetNumber;i <=maxoff;i=OffsetNumberNext(i))
|
433 | 418 | {
|
434 |
| -cur=arr[i-1].key; |
435 |
| -if (cur->low.x-pageunion.low.x<pageunion.high.x-cur->high.x) |
436 |
| -ADDLIST(listL,unionL,posL,arr[i-1].pos); |
437 |
| -elseif (cur->low.x-pageunion.low.x==pageunion.high.x-cur->high.x) |
| 419 | +cur=DatumGetBoxP(entryvec->vector[i].key); |
| 420 | + |
| 421 | +CenterX= ((double)cur->high.x+ (double)cur->low.x)/2.0; |
| 422 | +CenterY= ((double)cur->high.y+ (double)cur->low.y)/2.0; |
| 423 | + |
| 424 | +if (CenterX<avgCenterX) |
| 425 | +ADDLIST(listL,unionL,posL,i); |
| 426 | +elseif (CenterX==avgCenterX) |
438 | 427 | {
|
439 | 428 | if (posL>posR)
|
440 |
| -ADDLIST(listR,unionR,posR,arr[i-1].pos); |
| 429 | +ADDLIST(listR,unionR,posR,i); |
441 | 430 | else
|
442 |
| -ADDLIST(listL,unionL,posL,arr[i-1].pos); |
| 431 | +ADDLIST(listL,unionL,posL,i); |
443 | 432 | }
|
444 | 433 | else
|
445 |
| -ADDLIST(listR,unionR,posR,arr[i-1].pos); |
| 434 | +ADDLIST(listR,unionR,posR,i); |
446 | 435 |
|
447 |
| -if (cur->low.y-pageunion.low.y<pageunion.high.y-cur->high.y) |
448 |
| -ADDLIST(listB,unionB,posB,arr[i-1].pos); |
449 |
| -elseif (cur->low.y-pageunion.low.y==pageunion.high.y-cur->high.y) |
| 436 | +if (CenterY<avgCenterY) |
| 437 | +ADDLIST(listB,unionB,posB,i); |
| 438 | +elseif (CenterY==avgCenterY) |
450 | 439 | {
|
451 | 440 | if (posB>posT)
|
452 |
| -ADDLIST(listT,unionT,posT,arr[i-1].pos); |
| 441 | +ADDLIST(listT,unionT,posT,i); |
453 | 442 | else
|
454 |
| -ADDLIST(listB,unionB,posB,arr[i-1].pos); |
| 443 | +ADDLIST(listB,unionB,posB,i); |
455 | 444 | }
|
456 |
| -else |
457 |
| -ADDLIST(listT,unionT,posT,arr[i-1].pos); |
| 445 | +else |
| 446 | +ADDLIST(listT,unionT,posT,i); |
458 | 447 | }
|
459 | 448 | }
|
460 | 449 |
|
|