19 #include "order/order_internal.h"
85 if ( order == NULL ) {
86 pastix_print_error(
"orderSupernodes: invalid order pointer" );
90 lvl_kway = pastix_imax( lvl_proj, lvl_kway );
112 MALLOC_INTERN( n_levels, graph->n,
int );
113 for( sn_id=0; sn_id<order->
cblknbr; sn_id++ ) {
117 for(i=order->
rangtab[sn_id]; i<order->rangtab[sn_id+1]; i++) {
118 n_levels[ order->
peritab[i] ] = level;
127 MALLOC_INTERN( new_selevtx, order->
vertnbr, int8_t );
131 memset( new_selevtx, 0, order->
vertnbr *
sizeof(int8_t) );
133 new_cblknbr = sn_first;
135 for (sn_id = sn_first; sn_id < order->
cblknbr; sn_id++) {
136 pastix_graph_t sn_graph;
140 pastix_int_t sn_nbpart_proj, sn_nbparts, sn_nbparts_max;
142 perm_treetab[sn_id-sn_first] = new_cblknbr;
146 lnode = order->
rangtab[sn_id+1];
147 sn_vertnbr = lnode - fnode;
151 if ( (sn_level > (lvl_kway)) ||
152 (sn_nbparts_max == 1) ||
153 ((sn_id == order->
cblknbr-1) && (do_schur)) )
155 new_treetab[ new_cblknbr ] = order->
treetab[sn_id];
157 new_rangtab[ new_cblknbr ] = lnode;
162 fprintf( stdout,
" - Working on cblk %ld (level= %d, n= %ld):\n",
163 (
long)sn_id, (
int)sn_level, (
long)(lnode-fnode) );
170 memset( &sn_graph, 0,
sizeof(pastix_graph_t) );
180 if ( ret != EXIT_SUCCESS ) {
181 fprintf(stderr,
"Fatal error in graphIsolateSupernode()!\n");
184 assert( sn_vertnbr == sn_graph.n );
190 ( sn_level <= lvl_proj ) &&
194 memset( depth_size, 0, max_depth *
sizeof(
pastix_int_t) );
203 &sn_graph, &sn_order,
204 fnode, lnode, sn_level,
205 max_distance, max_depth, max_width,
211 fprintf(stdout,
" - Results of the projection:\n" );
212 for( i=0; i<max_depth; i++ ) {
213 fprintf( stdout,
" - At level %d: %8ld\n",
214 (
int)(i+1), (
long)depth_size[i] );
226 for( i=0; i<max_depth; i++ ) {
227 totalsel += depth_size[i];
230 if ( totalsel > selecmax ) {
234 total -= depth_size[i];
235 selected += depth_size[i];
255 fprintf( stdout,
" - %ld nodes selected, %ld remains for K-Way\n",
256 (
long)(sn_vertnbr - total), (
long)(total) );
263 if ( (sn_vertnbr - total) == 0 ) {
275 sn_nbpart_proj = sn_nbparts;
289 if ( nbpart_kway < 2 ) {
294 if ( sn_nbparts > 0 ) {
295 pastix_graph_t tmpgraph;
296 memset( &tmpgraph, 0,
sizeof(pastix_graph_t) );
307 memcpy( &sn_graph, &tmpgraph,
sizeof(pastix_graph_t) );
325 fprintf(stdout,
" - Connected components: %ld\n", (
long)comp_nbr );
329 for( i=0; i<comp_nbr; i++) {
337 cp_sz = comp_sze[cp_id];
342 if ( smallcp_id == -1 ) {
347 for( i=0; (i<sn_graph.n) && (cp_sz>0); i++) {
348 if ( comp_vtx[i] == cp_id ) {
349 comp_vtx[i] = smallcp_id;
354 comp_sze[ smallcp_id ] = smallcp_sz;
359 if ( nbpart_kway < 2 ) {
383 &comp_nbr, comp_sze, comp_vtx,
384 cp_id, nbpart_kway );
390 if ( comp_nbr > 1 ) {
392 sortptr[0] = comp_vtx;
393 sortptr[1] = order->
peritab + fnode;
395 qsort2IntAsc( sortptr, sn_graph.n );
398 for(i=comp_nbr-1; i>=0; i--) {
399 if (comp_sze[i] > 0) {
412 if ( sn_vertnbr > 0 ) {
417 assert( sn_nbparts >= 1 );
418 assert( new_rangtab[ new_cblknbr ] == fnode );
422 new_selevtx[ new_cblknbr ] = ( sn_nbparts-1 < sn_nbpart_proj ) ? SYMBCBLK_PROJ : SYMBCBLK_KWAY;
424 new_rangtab[ new_cblknbr ] = fnode;
427 assert( fnode <= lnode );
432 for(i=sn_nbparts-2; i>=0; i--)
435 new_treetab[new_cblknbr-1] = -1 - new_cblknbr;
436 new_selevtx[ new_cblknbr ] = ( i < sn_nbpart_proj ) ? SYMBCBLK_PROJ : SYMBCBLK_KWAY;
439 new_rangtab[new_cblknbr] = fnode;
442 assert( fnode <= lnode );
445 new_treetab[ new_cblknbr-1 ] = order->
treetab[sn_id];
448 for (i=order->
rangtab[sn_id]; i<order->rangtab[sn_id+1]; i++){
455 assert( new_rangtab[new_cblknbr] == order->
vertnbr );
457 if ( n_levels != NULL ) {
460 if ( depth_size != NULL ) {
469 memFree_null( order->
treetab );
473 oldtree = new_treetab;
474 for(i=0; i<new_cblknbr; i++, newtree++, oldtree++) {
475 if ( *oldtree >= sn_first ) {
476 *newtree = perm_treetab[ *oldtree - sn_first ];
478 else if ( *oldtree >= 0 ) {
481 else if ( *oldtree == -1 ) {
486 *newtree = - *oldtree - 1;
489 memFree_null( new_treetab );
490 memFree_null( perm_treetab );
498 order->
selevtx = realloc( new_selevtx, new_cblknbr *
sizeof(int8_t) );
501 printf(
"pastixOrderCheck() at the end of OrderSupernodes() failed !!!");
BEGIN_C_DECLS typedef int pastix_int_t
static pastix_int_t eTreeRoot(const EliminTree *etree)
Return the root of the elimination tree.
pastix_int_t eTreeGetLevelMinIdx(const EliminTree *, pastix_int_t, pastix_int_t, pastix_int_t)
Return the smallest index of the nodes belonging to the level lvl in the elimination tree.
pastix_int_t eTreeComputeLevels(EliminTree *, pastix_int_t, pastix_int_t)
Compute the number of level existing below a given node.
pastix_int_t extendint_Size(const ExtendVectorINT *)
Return the number of element stored in the vector.
void extendint_Clear(ExtendVectorINT *)
Cleanup the vector.
pastix_int_t extendint_Read(const ExtendVectorINT *, pastix_int_t)
Return the element of index eltnum.
pastix_int_t * extendint_Init(ExtendVectorINT *, pastix_int_t)
Initialize the extendVector structure with the initial size given.
void extendint_Add(ExtendVectorINT *, pastix_int_t)
Add an element elt to the end of the vector.
void extendint_Exit(ExtendVectorINT *)
Free the extendVector structure.
The extend integer array structure.
static void pqueuePush1(pastix_queue_t *q, pastix_int_t elt, double key1)
Push an element with a single key.
void pqueueExit(pastix_queue_t *)
Free the structure associated to the queue.
pastix_int_t pqueueSize(const pastix_queue_t *)
Return the size of the queue.
static pastix_int_t pqueuePop(pastix_queue_t *q)
Pop the head of the queue whithout returning the keys.
int pqueueInit(pastix_queue_t *, pastix_int_t)
Initialize the queue structure with an initial space to store the elements.
enum pastix_split_e pastix_split_t
Splitting strategy available for IPARM_SPLITTING_STRATEGY parameter.
@ IPARM_COMPRESS_MIN_WIDTH
@ IPARM_SPLITTING_PROJECTIONS_DISTANCE
@ IPARM_SPLITTING_LEVELS_PROJECTIONS
@ IPARM_SPLITTING_STRATEGY
@ IPARM_SPLITTING_LEVELS_KWAY
@ IPARM_SPLITTING_PROJECTIONS_WIDTH
@ IPARM_SPLITTING_PROJECTIONS_DEPTH
@ PASTIX_ERR_BADPARAMETER
@ PastixSplitKwayProjections
void graphExit(pastix_graph_t *graph)
Free the content of the graph structure.
pastix_int_t graphIsolateConnectedComponents(const pastix_graph_t *graph, pastix_int_t *comp_vtx, pastix_int_t *comp_sze)
Isolate the connected components from the original graph.
void graphComputeProjection(const pastix_graph_t *graph, const int *vertlvl, pastix_order_t *order, const pastix_graph_t *subgraph, pastix_order_t *suborder, pastix_int_t fnode, pastix_int_t lnode, pastix_int_t sn_level, pastix_int_t distance, pastix_int_t maxdepth, pastix_int_t maxwidth, pastix_int_t *depthsze)
TODO.
int graphIsolateRange(const pastix_graph_t *graphIn, const pastix_order_t *order, pastix_graph_t *graphOut, pastix_int_t fnode, pastix_int_t lnode, pastix_int_t distance)
Isolate the subgraph associated to a range of unknowns in the permuted graph.
int graphComputeKway(const pastix_graph_t *graph, pastix_order_t *order, pastix_int_t *peritab, pastix_int_t *comp_nbr, pastix_int_t *comp_sze, pastix_int_t *comp_vtx, pastix_int_t comp_id, pastix_int_t nbpart)
Compute the K-way partition of a given set of unknowns.
void pastixOrderBase(pastix_order_t *ordeptr, pastix_int_t baseval)
This routine sets the base of the given ordering structure to the given base value.
pastix_int_t orderSupernodes(const pastix_graph_t *graph, pastix_order_t *order, EliminTree *etree, pastix_int_t *iparm, int do_schur)
Order the supernodes with one of the clustering strategies.
int pastixOrderCheck(const pastix_order_t *ordeptr)
This routine checks the correctness of the ordering structure.
int pastixOrderAllocId(pastix_order_t *ordeptr, pastix_int_t vertnbr)
Allocate the order structure for a given number of vertices with no cblk, and id permutation.
void pastixOrderExit(pastix_order_t *ordeptr)
Free the arrays initialized in the order structure.