Exemple #1
0
/*
 * Post order a tree
 */
int *TreePostorder(
	int n,
	int *parent
)
{
	int	v, dad;

	/* Allocate storage for working arrays and results	*/
	first_kid = 	mxCallocInt (n+1);
	next_kid  = 	mxCallocInt (n+1);
	post	  = 	mxCallocInt (n+1);

	/* Set up structure describing children */
	for (v = 0; v <= n; first_kid[v++] = -1);
	for (v = n-1; v >= 0; v--) {
		dad = parent[v];
		next_kid[v] = first_kid[dad];
		first_kid[dad] = v;
	}

	/* Depth-first search from dummy root vertex #n */
	postnum = 0;
	etdfs (n);

	SUPERLU_FREE (first_kid);
	SUPERLU_FREE (next_kid);
	return post;
}
Exemple #2
0
/*
 * Nonsymmetric elimination tree
 */
int
sp_coletree(
	    int *acolst, int *acolend, /* column start and end past 1 */
	    int *arow,                 /* row indices of A */
	    int nr, int nc,            /* dimension of A */
	    int *parent	               /* parent in elim tree */
	    )
{
	int	*root;			/* root of subtee of etree 	*/
	int     *firstcol;		/* first nonzero col in each row*/
	int	rset, cset;             
	int	row, col;
	int	rroot;
	int	p;
	int     *pp;

	root = mxCallocInt (nc);
	initialize_disjoint_sets (nc, &pp);

	/* Compute firstcol[row] = first nonzero column in row */

	firstcol = mxCallocInt (nr);
	for (row = 0; row < nr; firstcol[row++] = nc);
	for (col = 0; col < nc; col++) 
		for (p = acolst[col]; p < acolend[col]; p++) {
			row = arow[p];
			firstcol[row] = SUPERLU_MIN(firstcol[row], col);
		}

	/* Compute etree by Liu's algorithm for symmetric matrices,
           except use (firstcol[r],c) in place of an edge (r,c) of A.
	   Thus each row clique in A'*A is replaced by a star
	   centered at its first vertex, which has the same fill. */

	for (col = 0; col < nc; col++) {
		cset = make_set (col, pp);
		root[cset] = col;
		parent[col] = nc; /* Matlab */
		for (p = acolst[col]; p < acolend[col]; p++) {
			row = firstcol[arow[p]];
			if (row >= col) continue;
			rset = find (row, pp);
			rroot = root[rset];
			if (rroot != col) {
				parent[rroot] = col;
				cset = link (cset, rset, pp);
				root[cset] = col;
			}
		}
	}

	SUPERLU_FREE (root);
	SUPERLU_FREE (firstcol);
	finalize_disjoint_sets (pp);
	return 0;
}
Exemple #3
0
static
void initialize_disjoint_sets (
	int n
	)
{
	pp = mxCallocInt(n);
}
Exemple #4
0
static
void initialize_disjoint_sets (
			       int n,
			       int **pp
			       )
{
	(*pp) = mxCallocInt(n);
}
static
void initialize_disjoint_sets (
			       int_t n,
			       int_t **pp    /* parent array for sets */
			       )
{
	if ( !( (*pp) = mxCallocInt(n)) ) 
	    ABORT("mxCallocInit fails for pp[]");
}
/*
 * Post order a tree
 */
int_t *TreePostorder_dist(
			  int_t n,
			  int_t *parent
			  )
{
	int_t	v, dad;
	int_t   *first_kid, *next_kid, *post, postnum;

	/* Allocate storage for working arrays and results	*/
	if ( !(first_kid = mxCallocInt (n+1)) )
	    ABORT("mxCallocInt fails for first_kid[]");
	if ( !(next_kid = mxCallocInt (n+1)) )
	    ABORT("mxCallocInt fails for next_kid[]");
	if ( !(post = mxCallocInt (n+1)) )
	    ABORT("mxCallocInt fails for post[]");

	/* Set up structure describing children */
	for (v = 0; v <= n; first_kid[v++] = -1);
	for (v = n-1; v >= 0; v--) {
		dad = parent[v];
		next_kid[v] = first_kid[dad];
		first_kid[dad] = v;
	}

	/* Depth-first search from dummy root vertex #n */
	postnum = 0;
#if 0
	/* recursion */
	etdfs (n, first_kid, next_kid, post, &postnum);
#else
	/* no recursion */
	nr_etdfs(n, parent, first_kid, next_kid, post, postnum);
#endif

	SUPERLU_FREE(first_kid);
	SUPERLU_FREE(next_kid);
	return post;
}
/*! \brief Symmetric elimination tree
 *
 * <pre>
 *      p = spsymetree (A);
 *
 *      Find the elimination tree for symmetric matrix A.
 *      This uses Liu's algorithm, and runs in time O(nz*log n).
 *
 *      Input:
 *        Square sparse matrix A.  No check is made for symmetry;
 *        elements below and on the diagonal are ignored.
 *        Numeric values are ignored, so any explicit zeros are 
 *        treated as nonzero.
 *      Output:
 *        Integer array of parents representing the etree, with n
 *        meaning a root of the elimination forest.
 *      Note:  
 *        This routine uses only the upper triangle, while sparse
 *        Cholesky (as in spchol.c) uses only the lower.  Matlab's
 *        dense Cholesky uses only the upper.  This routine could
 *        be modified to use the lower triangle either by transposing
 *        the matrix or by traversing it by rows with auxiliary
 *        pointer and link arrays.
 *
 *      John R. Gilbert, Xerox, 10 Dec 1990
 *      Based on code by JRG dated 1987, 1988, and 1990.
 *      Modified by X.S. Li, November 1999.
 * </pre>
 */
int
sp_symetree_dist(
	    int_t *acolst, int_t *acolend, /* column starts and ends past 1 */
	    int_t *arow,            /* row indices of A */
	    int_t n,                /* dimension of A */
	    int_t *parent	    /* parent in elim tree */
	    )
{
	int_t	*root;		    /* root of subtee of etree 	*/
	int_t	rset, cset;             
	int_t	row, col;
	int_t	rroot;
	int_t	p;
	int_t   *pp;

#if ( DEBUGlevel>=1 )
	CHECK_MALLOC(0, "Enter sp_symetree()");
#endif

	root = mxCallocInt (n);
	initialize_disjoint_sets (n, &pp);

	for (col = 0; col < n; col++) {
		cset = make_set (col, pp);
		root[cset] = col;
		parent[col] = n; /* Matlab */
		for (p = acolst[col]; p < acolend[col]; p++) {
			row = arow[p];
			if (row >= col) continue;
			rset = find (row, pp);
			rroot = root[rset];
			if (rroot != col) {
				parent[rroot] = col;
				cset = link (cset, rset, pp);
				root[cset] = col;
			}
		}
	}
	SUPERLU_FREE (root);
	finalize_disjoint_sets (pp);

#if ( DEBUGlevel>=1 )
	CHECK_MALLOC(0, "Exit sp_symetree()");
#endif
	return 0;
} /* SP_SYMETREE_DIST */
Exemple #8
0
/*
 * Symmetric elimination tree
 */
int
sp_symetree(
	    int *acolst, int *acolend, /* column starts and ends past 1 */
	    int *arow,            /* row indices of A */
	    int n,                /* dimension of A */
	    int *parent	    /* parent in elim tree */
	    )
{
	int	*root;		    /* root of subtree of etree 	*/
	int	rset, cset;             
	int	row, col;
	int	rroot;
	int	p;

	root = mxCallocInt (n);
	initialize_disjoint_sets (n);

	for (col = 0; col < n; col++) {
		cset = make_set (col);
		root[cset] = col;
		parent[col] = n; /* Matlab */
		for (p = acolst[col]; p < acolend[col]; p++) {
			row = arow[p];
			if (row >= col) continue;
			rset = find (row);
			rroot = root[rset];
			if (rroot != col) {
				parent[rroot] = col;
				cset = link (cset, rset);
				root[cset] = col;
			}
		}
	}
	SUPERLU_FREE (root);
	finalize_disjoint_sets ();
	return 0;
} /* SP_SYMETREE */