ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE-4/src/QuickHull/user.c
Revision: 3138
Committed: Tue May 29 22:51:00 2007 UTC (17 years, 11 months ago) by chuckv
Content type: text/plain
File size: 11132 byte(s)
Log Message:
Addded QuickHull to cvs.

File Contents

# User Rev Content
1 chuckv 3138 /*<html><pre> -<a href="qh-user.htm"
2     >-------------------------------</a><a name="TOP">-</a>
3    
4     user.c
5     user redefinable functions
6    
7     see README.txt see COPYING.txt for copyright information.
8    
9     see qhull.h for data structures, macros, and user-callable functions.
10    
11     see user_eg.c, unix.c, and qhull_interface.cpp for examples.
12    
13     see user.h for user-definable constants
14    
15     please use qh_NOmem in mem.h to turn off memory management
16     please use qh_NOmerge in user.h to turn off facet merging
17     set qh_KEEPstatistics in user.h to 0 to turn off statistics
18    
19     This is unsupported software. You're welcome to make changes,
20     but you're on your own if something goes wrong. Use 'Tc' to
21     check frequently. Usually qhull will report an error if
22     a data structure becomes inconsistent. If so, it also reports
23     the last point added to the hull, e.g., 102. You can then trace
24     the execution of qhull with "T4P102".
25    
26     Please report any errors that you fix to qhull@qhull.org
27    
28     call_qhull is a template for calling qhull from within your application
29    
30     if you recompile and load this module, then user.o will not be loaded
31     from qhull.a
32    
33     you can add additional quick allocation sizes in qh_user_memsizes
34    
35     if the other functions here are redefined to not use qh_print...,
36     then io.o will not be loaded from qhull.a. See user_eg.c for an
37     example. We recommend keeping io.o for the extra debugging
38     information it supplies.
39     */
40    
41     #include "QuickHull/qhull_a.h"
42    
43     /*-<a href="qh-user.htm#TOC"
44     >-------------------------------</a><a name="call_qhull">-</a>
45    
46     qh_call_qhull( void )
47     template for calling qhull from inside your program
48     remove #if 0, #endif to compile
49    
50     returns:
51     exit code (see qh_ERR... in qhull.h)
52     all memory freed
53    
54     notes:
55     This can be called any number of times.
56    
57     see:
58     qh_call_qhull_once()
59    
60     */
61     #if 0
62     {
63     int dim; /* dimension of points */
64     int numpoints; /* number of points */
65     coordT *points; /* array of coordinates for each point */
66     boolT ismalloc; /* True if qhull should free points in qh_freeqhull() or reallocation */
67     char flags[]= "qhull Tv"; /* option flags for qhull, see qh_opt.htm */
68     FILE *outfile= stdout; /* output from qh_produce_output()
69     please use NULL to skip qh_produce_output() */
70     FILE *errfile= stderr; /* error messages from qhull code */
71     int exitcode; /* 0 if no error from qhull */
72     facetT *facet; /* set by FORALLfacets */
73     int curlong, totlong; /* memory remaining after qh_memfreeshort */
74    
75     /* initialize dim, numpoints, points[], ismalloc here */
76     exitcode= qh_new_qhull (dim, numpoints, points, ismalloc,
77     flags, outfile, errfile);
78     if (!exitcode) { /* if no error */
79     /* 'qh facet_list' contains the convex hull */
80     FORALLfacets {
81     /* ... your code ... */
82     }
83     }
84     qh_freeqhull(!qh_ALL);
85     qh_memfreeshort (&curlong, &totlong);
86     if (curlong || totlong)
87     fprintf (errfile, "qhull internal warning (main): did not free %d bytes of long memory (%d pieces)\n", totlong, curlong);
88     }
89     #endif
90    
91     /*-<a href="qh-user.htm#TOC"
92     >-------------------------------</a><a name="new_qhull">-</a>
93    
94     qh_new_qhull( dim, numpoints, points, ismalloc, qhull_cmd, outfile, errfile )
95     build new qhull data structure and return exitcode (0 if no errors)
96    
97     notes:
98     do not modify points until finished with results.
99     The qhull data structure contains pointers into the points array.
100     do not call qhull functions before qh_new_qhull().
101     The qhull data structure is not initialized until qh_new_qhull().
102    
103     outfile may be null
104     qhull_cmd must start with "qhull "
105     projects points to a new point array for Delaunay triangulations ('d' and 'v')
106     transforms points into a new point array for halfspace intersection ('H')
107    
108    
109     To allow multiple, concurrent calls to qhull()
110     - set qh_QHpointer in user.h
111     - use qh_save_qhull and qh_restore_qhull to swap the global data structure between calls.
112     - use qh_freeqhull(qh_ALL) to free intermediate convex hulls
113    
114     see:
115     user_eg.c for an example
116     */
117     int qh_new_qhull (int dim, int numpoints, coordT *points, boolT ismalloc,
118     char *qhull_cmd, FILE *outfile, FILE *errfile) {
119     int exitcode, hulldim;
120     boolT new_ismalloc;
121     static boolT firstcall = True;
122     coordT *new_points;
123    
124     if (firstcall) {
125     qh_meminit (errfile);
126     firstcall= False;
127     }
128     if (strncmp (qhull_cmd,"qhull ", 6)) {
129     fprintf (errfile, "qh_new_qhull: start qhull_cmd argument with \"qhull \"\n");
130     exit(1);
131     }
132     qh_initqhull_start (NULL, outfile, errfile);
133     trace1(( qh ferr, "qh_new_qhull: build new Qhull for %d %d-d points with %s\n", numpoints, dim, qhull_cmd));
134     exitcode = setjmp (qh errexit);
135     if (!exitcode)
136     {
137     qh NOerrexit = False;
138     qh_initflags (qhull_cmd);
139     if (qh DELAUNAY)
140     qh PROJECTdelaunay= True;
141     if (qh HALFspace) {
142     /* points is an array of halfspaces,
143     the last coordinate of each halfspace is its offset */
144     hulldim= dim-1;
145     qh_setfeasible (hulldim);
146     new_points= qh_sethalfspace_all (dim, numpoints, points, qh feasible_point);
147     new_ismalloc= True;
148     if (ismalloc)
149     free (points);
150     }else {
151     hulldim= dim;
152     new_points= points;
153     new_ismalloc= ismalloc;
154     }
155     qh_init_B (new_points, numpoints, hulldim, new_ismalloc);
156     qh_qhull();
157     qh_check_output();
158     if (outfile)
159     qh_produce_output();
160     if (qh VERIFYoutput && !qh STOPpoint && !qh STOPcone)
161     qh_check_points();
162     }
163     qh NOerrexit = True;
164     return exitcode;
165     } /* new_qhull */
166    
167     /*-<a href="qh-user.htm#TOC"
168     >-------------------------------</a><a name="errexit">-</a>
169    
170     qh_errexit( exitcode, facet, ridge )
171     report and exit from an error
172     report facet and ridge if non-NULL
173     reports useful information such as last point processed
174     set qh.FORCEoutput to print neighborhood of facet
175    
176     see:
177     qh_errexit2() in qhull.c for printing 2 facets
178    
179     design:
180     check for error within error processing
181     compute qh.hulltime
182     print facet and ridge (if any)
183     report commandString, options, qh.furthest_id
184     print summary and statistics (including precision statistics)
185     if qh_ERRsingular
186     print help text for singular data set
187     exit program via long jump (if defined) or exit()
188     */
189     void qh_errexit(int exitcode, facetT *facet, ridgeT *ridge) {
190    
191     if (qh ERREXITcalled) {
192     fprintf (qh ferr, "\nqhull error while processing previous error. Exit program\n");
193     exit(1);
194     }
195     qh ERREXITcalled= True;
196     if (!qh QHULLfinished)
197     qh hulltime= qh_CPUclock - qh hulltime;
198     qh_errprint("ERRONEOUS", facet, NULL, ridge, NULL);
199     fprintf (qh ferr, "\nWhile executing: %s | %s\n", qh rbox_command, qh qhull_command);
200     fprintf(qh ferr, "Options selected for Qhull %s:\n%s\n", qh_version, qh qhull_options);
201     if (qh furthest_id >= 0) {
202     fprintf(qh ferr, "Last point added to hull was p%d.", qh furthest_id);
203     if (zzval_(Ztotmerge))
204     fprintf(qh ferr, " Last merge was #%d.", zzval_(Ztotmerge));
205     if (qh QHULLfinished)
206     fprintf(qh ferr, "\nQhull has finished constructing the hull.");
207     else if (qh POSTmerging)
208     fprintf(qh ferr, "\nQhull has started post-merging.");
209     fprintf (qh ferr, "\n");
210     }
211     if (qh FORCEoutput && (qh QHULLfinished || (!facet && !ridge)))
212     qh_produce_output();
213     else {
214     if (exitcode != qh_ERRsingular && zzval_(Zsetplane) > qh hull_dim+1) {
215     fprintf (qh ferr, "\nAt error exit:\n");
216     qh_printsummary (qh ferr);
217     if (qh PRINTstatistics) {
218     qh_collectstatistics();
219     qh_printstatistics(qh ferr, "at error exit");
220     qh_memstatistics (qh ferr);
221     }
222     }
223     if (qh PRINTprecision)
224     qh_printstats (qh ferr, qhstat precision, NULL);
225     }
226     if (!exitcode)
227     exitcode= qh_ERRqhull;
228     else if (exitcode == qh_ERRsingular)
229     qh_printhelp_singular(qh ferr);
230     else if (exitcode == qh_ERRprec && !qh PREmerge)
231     qh_printhelp_degenerate (qh ferr);
232     if (qh NOerrexit) {
233     fprintf (qh ferr, "qhull error while ending program. Exit program\n");
234     exit(1);
235     }
236     qh NOerrexit= True;
237     longjmp(qh errexit, exitcode);
238     } /* errexit */
239    
240    
241     /*-<a href="qh-user.htm#TOC"
242     >-------------------------------</a><a name="errprint">-</a>
243    
244     qh_errprint( fp, string, atfacet, otherfacet, atridge, atvertex )
245     prints out the information of facets and ridges to fp
246     also prints neighbors and geomview output
247    
248     notes:
249     except for string, any parameter may be NULL
250     */
251     void qh_errprint(char *string, facetT *atfacet, facetT *otherfacet, ridgeT *atridge, vertexT *atvertex) {
252     int i;
253    
254     if (atfacet) {
255     fprintf(qh ferr, "%s FACET:\n", string);
256     qh_printfacet(qh ferr, atfacet);
257     }
258     if (otherfacet) {
259     fprintf(qh ferr, "%s OTHER FACET:\n", string);
260     qh_printfacet(qh ferr, otherfacet);
261     }
262     if (atridge) {
263     fprintf(qh ferr, "%s RIDGE:\n", string);
264     qh_printridge(qh ferr, atridge);
265     if (atridge->top && atridge->top != atfacet && atridge->top != otherfacet)
266     qh_printfacet(qh ferr, atridge->top);
267     if (atridge->bottom
268     && atridge->bottom != atfacet && atridge->bottom != otherfacet)
269     qh_printfacet(qh ferr, atridge->bottom);
270     if (!atfacet)
271     atfacet= atridge->top;
272     if (!otherfacet)
273     otherfacet= otherfacet_(atridge, atfacet);
274     }
275     if (atvertex) {
276     fprintf(qh ferr, "%s VERTEX:\n", string);
277     qh_printvertex (qh ferr, atvertex);
278     }
279     if (qh fout && qh FORCEoutput && atfacet && !qh QHULLfinished && !qh IStracing) {
280     fprintf(qh ferr, "ERRONEOUS and NEIGHBORING FACETS to output\n");
281     for (i= 0; i < qh_PRINTEND; i++) /* use fout for geomview output */
282     qh_printneighborhood (qh fout, qh PRINTout[i], atfacet, otherfacet,
283     !qh_ALL);
284     }
285     } /* errprint */
286    
287    
288     /*-<a href="qh-user.htm#TOC"
289     >-------------------------------</a><a name="printfacetlist">-</a>
290    
291     qh_printfacetlist( fp, facetlist, facets, printall )
292     print all fields for a facet list and/or set of facets to fp
293     if !printall,
294     only prints good facets
295    
296     notes:
297     also prints all vertices
298     */
299     void qh_printfacetlist(facetT *facetlist, setT *facets, boolT printall) {
300     facetT *facet, **facetp;
301    
302     qh_printbegin (qh ferr, qh_PRINTfacets, facetlist, facets, printall);
303     FORALLfacet_(facetlist)
304     qh_printafacet(qh ferr, qh_PRINTfacets, facet, printall);
305     FOREACHfacet_(facets)
306     qh_printafacet(qh ferr, qh_PRINTfacets, facet, printall);
307     qh_printend (qh ferr, qh_PRINTfacets, facetlist, facets, printall);
308     } /* printfacetlist */
309    
310    
311     /*-<a href="qh-globa.htm#TOC"
312     >-------------------------------</a><a name="user_memsizes">-</a>
313    
314     qh_user_memsizes()
315     allocate up to 10 additional, quick allocation sizes
316    
317     notes:
318     increase maximum number of allocations in qh_initqhull_mem()
319     */
320     void qh_user_memsizes (void) {
321    
322     /* qh_memsize (size); */
323     } /* user_memsizes */
324