/* Copyright (C) 2000 Kai Habel
**
** This program is free software; you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by
** the Free Software Foundation; either version 2 of the License, or
** (at your option) any later version.
**
** This program is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
** GNU General Public License for more details.
**
** You should have received a copy of the GNU General Public License
** along with this program; if not, write to the Free Software
** Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
*/
/*
29. July 2000 - Kai Habel: first release
2002-04-22 Paul Kienzle
* Use warning(...) function rather than writing to cerr
*/
extern "C" {
#include "qhull/qhull_a.h"
}
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <octave/oct.h>
#ifdef NEED_QHULL_VERSION
char qh_version[] = "convhulln.oct 2003-12-14";
#endif
char flags[250];
const char *options;
DEFUN_DLD (convhulln, args, ,
"-*- texinfo -*-\n\
@deftypefn {Loadable Function} {@var{H} =} convhulln (@var{p}[, @var{opt}])\n\
Returns an index vector to the points of the enclosing convex hull.\n\
The input matrix of size [n, dim] contains n points of dimension dim.\n\n\
If a second optional argument is given, it must be a string containing\n\
extra options for the underlying qhull command. (See the Qhull\n\
documentation for the available options.)\n\n\
@seealso{convhull, delaunayn}\n\
@end deftypefn")
{
octave_value_list retval;
int nargin = args.length();
if (nargin < 1 || nargin > 2) {
print_usage ("convhulln(p,[opt])");
return retval;
}
if (nargin == 2) {
if ( ! args (1).is_string () ) {
error ("convhulln: second argument must be a string");
return retval;
}
options = args (1).string_value().c_str();
}
else
options = "";
Matrix p(args(0).matrix_value());
const int dim = p.columns();
const int n = p.rows();
p = p.transpose();
double *pt_array = p.fortran_vec();
boolT ismalloc = False;
// hmm lot's of options for qhull here
sprintf(flags,"qhull s Qt Tcv %s",options);
if (!qh_new_qhull (dim,n,pt_array,ismalloc,flags,NULL,stderr)) {
// If you want some debugging information replace the NULL
// pointer with stdout
vertexT *vertex,**vertexp;
facetT *facet;
unsigned int n = qh num_facets;
Matrix idx(n,dim);
qh_vertexneighbors();
int i=0;
FORALLfacets {
int j=0;
//std::cout << "Current index " << i << "," << j << std::endl << std::flush;
// qh_printfacet(stdout,facet);
FOREACHvertex_ (facet->vertices) {
// qh_printvertex(stdout,vertex);
if (j >= dim)
warning("extra vertex %d of facet %d = %d",
j++,i,1+qh_pointid(vertex->point));
else
idx(i,j++)= 1 + qh_pointid(vertex->point);
}
if (j < dim) warning("facet %d only has %d vertices",i,j);
i++;
}
retval(0)=octave_value(idx);
}
qh_freeqhull(!qh_ALL);
//free long memory
int curlong, totlong;
qh_memfreeshort (&curlong, &totlong);
//free short memory and memory allocator
if (curlong || totlong) {
warning("convhulln: did not free %d bytes of long memory (%d pieces)",
totlong, curlong);
}
return retval;
}
syntax highlighted by Code2HTML, v. 0.9.1