/** * In linear time, group the sub-array ar[left, right) around a pivot * element ar[right] by storing pivot into its proper location, * store, within the sub-array (whose location is returned by this * function) and ensuring that all ar[left,store) <= pivot and all * ar[store+1,right) > pivot. * * ASSUMES THAT pivot value is already placed in ar[right] and that * ar[left] <= ar[mid] <= ar[right]. * * @param ar array of elements to be sorted. * @param left lower bound index position (inclusive) * @param right upper bound index position (exclusive) * @return location of the pivot index properly positioned. */ void *partition (void *const pbase, size_t n, size_t s, int(*cmp)(const void *,const void *)) { void *store = (void*)((char*)pbase+(n-1)*s); void *left = (void*)((char*)pbase+s); void *right = (void*)((char*)store-s); do { while (cmp(left,store) < 0) { left += s; ADD_COMP; } while (cmp(store,right) < 0) { right -= s; ADD_COMP; } ADD_COMP; ADD_COMP; if (left < right) { ADD_COMP; swapcode(s,left,right); left += s; right -= s; } else if (left == right) { ADD_COMP; ADD_COMP; break; } else { ADD_COMP; ADD_COMP; } } while (left <= right); swapcode(s, left, store); return left; }
static inline void swapfunc(char *a, char *b, size_t n, int swaptype) { if (swaptype <= 1) swapcode(PORT_LONG, a, b, n) else swapcode(char, a, b, n) }
void clipline(dcpt winmin,dcpt winmax,wcpt2 p1,wcpt2 p2) { unsigned char encode(wcpt2,dcpt,dcpt); unsigned char code1,code2; int done = 0 , draw = 0; float m; void swapcode(unsigned char *c1,unsigned char *c2); void swappts(wcpt2 *p1,wcpt2 *p2); while(!done) { code1 = encode(p1,winmin,winmax); code2 = encode(p2,winmin,winmax); if(ACCEPT(code1,code2)) { draw = 1; done = 1; } else if(REJECT(code1,code2)) done = 1; else if(INSIDE(code1)) { swappts(&p1,&p2); swapcode(&code1,&code2); } if(code1 & LEFT_EDGE) { p1.y += (winmin.x - p1.x) * (p2.y - p1.y) / (p2.x - p1.x); p1.x = winmin.x; } else if(code1 & RIGHT_EDGE) { p1.y += (winmax.x - p1.x) * (p2.y - p1.y) / (p2.x - p1.x); p1.x = winmax.x; } else if(code1 & TOP_EDGE) { if(p2.x != p1.x) p1.x += (winmin.y - p1.y) * (p2.x - p1.x) / (p2.y - p1.y); p1.y = winmin.y; } else if(code1 & BOTTOM_EDGE) { if(p2.x != p1.x) p1.x += (winmax.y - p1.y) * (p2.x - p1.x) / (p2.y - p1.y); p1.y = winmax.y; } } if(draw) { setcolor(5); line(p1.x,p1.y,p2.x,p2.y); } }