23 idx_t i, ii,
j, k, jj, kk, nvtxs, nbnd, nswaps, nmind;
25 idx_t *mptr, *mind, *moved, *swaps;
28 idx_t higain, oldgain, mincut, initcut, mincutorder;
30 idx_t badmaxpwgt, mindiff, newdiff;
56 badmaxpwgt = (
idx_t)(mult*(pwgts[0]+pwgts[1]+pwgts[2]));
61 for (pass=0; pass<niter; pass++) {
62 iset(nvtxs, -1, moved);
67 initcut = mincut = graph->
mincut;
72 for (ii=0; ii<nbnd; ii++) {
73 i = bndind[swaps[ii]];
75 rpqInsert(queues[0], i, vwgt[i]-rinfo[i].edegrees[1]);
76 rpqInsert(queues[1], i, vwgt[i]-rinfo[i].edegrees[0]);
88 mindiff =
iabs(pwgts[0]-pwgts[1]);
89 to = (pwgts[0] < pwgts[1] ? 0 : 1);
90 for (nswaps=0; nswaps<nvtxs; nswaps++) {
93 if (u[0] != -1 && u[1] != -1) {
94 g[0] = vwgt[u[0]]-rinfo[u[0]].
edegrees[1];
95 g[1] = vwgt[u[1]]-rinfo[u[1]].
edegrees[0];
97 to = (g[0] > g[1] ? 0 : (g[0] < g[1] ? 1 : pass%2));
99 if (pwgts[to]+vwgt[u[to]] > badmaxpwgt)
102 else if (u[0] == -1 && u[1] == -1) {
105 else if (u[0] != -1 && pwgts[0]+vwgt[u[0]] <= badmaxpwgt) {
108 else if (u[1] != -1 && pwgts[1]+vwgt[u[1]] <= badmaxpwgt) {
117 if (moved[higain] == -1)
120 ASSERT(bndptr[higain] != -1);
124 if (nmind + xadj[higain+1]-xadj[higain] >= 2*nvtxs-1)
129 newdiff =
iabs(pwgts[to]+vwgt[higain] - (pwgts[other]-rinfo[higain].edegrees[other]));
130 if (pwgts[2] < mincut || (pwgts[2] == mincut && newdiff < mindiff)) {
132 mincutorder = nswaps;
136 if (nswaps - mincutorder > 2*limit ||
137 (nswaps - mincutorder > limit && pwgts[2] > 1.10*mincut)) {
144 pwgts[to] += vwgt[higain];
146 moved[higain] = nswaps;
147 swaps[nswaps] = higain;
153 for (j=xadj[higain]; j<xadj[higain+1]; j++) {
156 oldgain = vwgt[k]-rinfo[k].
edegrees[to];
157 rinfo[k].
edegrees[to] += vwgt[higain];
158 if (moved[k] == -1 || moved[k] == -(2+other))
159 rpqUpdate(queues[other], k, oldgain-vwgt[higain]);
161 else if (where[k] == other) {
162 ASSERTP(bndptr[k] == -1, (
"%"PRIDX
" %"PRIDX
" %"PRIDX
"\n", k, bndptr[k], where[k]));
167 pwgts[
other] -= vwgt[k];
170 edegrees[0] = edegrees[1] = 0;
171 for (jj=xadj[k]; jj<xadj[k+1]; jj++) {
174 edegrees[where[kk]] += vwgt[kk];
178 if (moved[kk] == -1 || moved[kk] == -(2+to))
179 rpqUpdate(queues[to], kk, oldgain+vwgt[k]);
184 if (moved[k] == -1) {
185 rpqInsert(queues[to], k, vwgt[k]-edegrees[other]);
190 mptr[nswaps+1] = nmind;
193 printf(
"Moved %6"PRIDX
" to %3"PRIDX
", Gain: %5"PRIDX
" [%5"PRIDX
"] [%4"PRIDX
" %4"PRIDX
"] \t[%5"PRIDX
" %5"PRIDX
" %5"PRIDX
"]\n", higain, to, g[to], g[other], vwgt[u[to]], vwgt[u[other]], pwgts[0], pwgts[1], pwgts[2]));
201 for (nswaps--; nswaps>mincutorder; nswaps--) {
202 higain = swaps[nswaps];
208 INC_DEC(pwgts[2], pwgts[to], vwgt[higain]);
213 edegrees[0] = edegrees[1] = 0;
214 for (j=xadj[higain]; j<xadj[higain+1]; j++) {
217 rinfo[k].
edegrees[to] -= vwgt[higain];
219 edegrees[where[k]] += vwgt[k];
223 for (j=mptr[nswaps]; j<mptr[nswaps+1]; j++) {
227 INC_DEC(pwgts[other], pwgts[2], vwgt[k]);
229 for (jj=xadj[k]; jj<xadj[k+1]; jj++) {
237 ASSERT(mincut == pwgts[2]);
240 printf(
"\tMinimum sep: %6"PRIDX
" at %5"PRIDX
", PWGTS: [%6"PRIDX
" %6"PRIDX
"], NBND: %6"PRIDX
"\n", mincut, mincutorder, pwgts[0], pwgts[1], nbnd));
245 if (mincutorder == -1 || mincut >= initcut)
265 idx_t i, ii,
j, k, jj, kk, nvtxs, nbnd, nswaps, nmind, iend;
267 idx_t *mptr, *mind, *swaps;
270 idx_t higain, mincut, initcut, mincutorder;
272 idx_t badmaxpwgt, mindiff, newdiff;
277 nvtxs = graph->
nvtxs;
284 where = graph->
where;
285 pwgts = graph->
pwgts;
295 badmaxpwgt = (
idx_t)(mult*(pwgts[0]+pwgts[1]+pwgts[2]));
300 to = (pwgts[0] < pwgts[1] ? 1 : 0);
301 for (pass=0; pass<2*niter; pass++) {
308 initcut = mincut = graph->
mincut;
313 for (ii=0; ii<nbnd; ii++) {
314 i = bndind[swaps[ii]];
316 rpqInsert(queue, i, vwgt[i]-rinfo[i].edegrees[other]);
329 mindiff =
iabs(pwgts[0]-pwgts[1]);
330 for (nswaps=0; nswaps<nvtxs; nswaps++) {
334 ASSERT(bndptr[higain] != -1);
338 if (nmind + xadj[higain+1]-xadj[higain] >= 2*nvtxs-1)
341 if (pwgts[to]+vwgt[higain] > badmaxpwgt)
346 newdiff =
iabs(pwgts[to]+vwgt[higain] - (pwgts[other]-rinfo[higain].edegrees[other]));
347 if (pwgts[2] < mincut || (pwgts[2] == mincut && newdiff < mindiff)) {
349 mincutorder = nswaps;
353 if (nswaps - mincutorder > 3*limit ||
354 (nswaps - mincutorder > limit && pwgts[2] > 1.10*mincut)) {
361 pwgts[to] += vwgt[higain];
363 swaps[nswaps] = higain;
370 for (j=xadj[higain]; j<xadj[higain+1]; j++) {
374 rinfo[k].
edegrees[to] += vwgt[higain];
376 else if (where[k] == other) {
377 ASSERTP(bndptr[k] == -1, (
"%"PRIDX
" %"PRIDX
" %"PRIDX
"\n", k, bndptr[k], where[k]));
382 pwgts[
other] -= vwgt[k];
385 edegrees[0] = edegrees[1] = 0;
386 for (jj=xadj[k], iend=xadj[k+1]; jj<iend; jj++) {
389 edegrees[where[kk]] += vwgt[kk];
394 rpqUpdate(queue, kk, vwgt[kk]-rinfo[kk].edegrees[other]);
399 rpqInsert(queue, k, vwgt[k]-edegrees[other]);
402 mptr[nswaps+1] = nmind;
407 printf(
"Moved %6"PRIDX
" to %3"PRIDX
", Gain: %5"PRIDX
" [%5"PRIDX
"] \t[%5"PRIDX
" %5"PRIDX
" %5"PRIDX
"] [%3"PRIDX
" %2"PRIDX
"]\n",
408 higain, to, (vwgt[higain]-rinfo[higain].edegrees[other]), vwgt[higain],
409 pwgts[0], pwgts[1], pwgts[2], nswaps, limit));
418 for (nswaps--; nswaps>mincutorder; nswaps--) {
419 higain = swaps[nswaps];
422 ASSERT(where[higain] == to);
424 INC_DEC(pwgts[2], pwgts[to], vwgt[higain]);
429 edegrees[0] = edegrees[1] = 0;
430 for (j=xadj[higain]; j<xadj[higain+1]; j++) {
433 rinfo[k].
edegrees[to] -= vwgt[higain];
435 edegrees[where[k]] += vwgt[k];
439 for (j=mptr[nswaps]; j<mptr[nswaps+1]; j++) {
443 INC_DEC(pwgts[other], pwgts[2], vwgt[k]);
445 for (jj=xadj[k], iend=xadj[k+1]; jj<iend; jj++) {
454 ASSERT(mincut == pwgts[2]);
457 printf(
"\tMinimum sep: %6"PRIDX
" at %5"PRIDX
", PWGTS: [%6"PRIDX
" %6"PRIDX
"], NBND: %6"PRIDX
"\n", mincut, mincutorder, pwgts[0], pwgts[1], nbnd));
462 if (pass%2 == 1 && (mincutorder == -1 || mincut >= initcut))
478 idx_t i, ii,
j, k, jj, kk, nvtxs, nbnd, nswaps, gain;
479 idx_t badmaxpwgt, higain, oldgain, pass, to,
other;
486 nvtxs = graph->
nvtxs;
493 where = graph->
where;
494 pwgts = graph->
pwgts;
499 badmaxpwgt = (
idx_t)(mult*(pwgts[0]+pwgts[1]));
500 if (
gk_max(pwgts[0], pwgts[1]) < badmaxpwgt)
502 if (
iabs(pwgts[0]-pwgts[1]) < 3*graph->
tvwgt[0]/nvtxs)
507 to = (pwgts[0] < pwgts[1] ? 0 : 1);
520 for (ii=0; ii<nbnd; ii++) {
521 i = bndind[perm[ii]];
523 rpqInsert(queue, i, vwgt[i]-rinfo[i].edegrees[other]);
532 for (nswaps=0; nswaps<nvtxs; nswaps++) {
539 badmaxpwgt = (
idx_t)(mult*(pwgts[0]+pwgts[1]));
542 if (pwgts[to] > pwgts[other])
546 if (gain < 0 && pwgts[other] < badmaxpwgt)
550 if (pwgts[to]+vwgt[higain] > badmaxpwgt)
553 ASSERT(bndptr[higain] != -1);
558 pwgts[to] += vwgt[higain];
562 printf(
"Moved %6"PRIDX
" to %3"PRIDX
", Gain: %3"PRIDX
", \t[%5"PRIDX
" %5"PRIDX
" %5"PRIDX
"]\n", higain, to, vwgt[higain]-rinfo[higain].edegrees[other], pwgts[0], pwgts[1], pwgts[2]));
568 for (j=xadj[higain]; j<xadj[higain+1]; j++) {
571 rinfo[k].
edegrees[to] += vwgt[higain];
573 else if (where[k] == other) {
574 ASSERTP(bndptr[k] == -1, (
"%"PRIDX
" %"PRIDX
" %"PRIDX
"\n", k, bndptr[k], where[k]));
578 pwgts[
other] -= vwgt[k];
581 edegrees[0] = edegrees[1] = 0;
582 for (jj=xadj[k]; jj<xadj[k+1]; jj++) {
585 edegrees[where[kk]] += vwgt[kk];
597 rpqInsert(queue, k, vwgt[k]-edegrees[other]);
603 printf(
"\tBalanced sep: %6"PRIDX
" at %4"PRIDX
", PWGTS: [%6"PRIDX
" %6"PRIDX
"], NBND: %6"PRIDX
"\n", pwgts[2], nswaps, pwgts[0], pwgts[1], nbnd));
idx_t idx_t idx_t idx_t * vwgt
#define gk_startcputimer(tmr)
#define BNDDelete(nbnd, bndind, bndptr, vtx)
#define irandArrayPermute
#define gk_stopcputimer(tmr)
#define ASSERTP(expr, msg)
#define CheckNodePartitionParams
NonlinearFactorGraph graph
void g(const string &key, int i)
#define ASSERT(expression)
void FM_2WayNodeBalance(ctrl_t *ctrl, graph_t *graph)
#define BNDInsert(nbnd, bndind, bndptr, vtx)
idx_t idx_t idx_t idx_t idx_t * perm
void FM_2WayNodeRefine1Sided(ctrl_t *ctrl, graph_t *graph, idx_t niter)
#define INC_DEC(a, b, val)
idx_t idx_t idx_t idx_t * where
idx_t idx_t idx_t * adjncy
void FM_2WayNodeRefine2Sided(ctrl_t *ctrl, graph_t *graph, idx_t niter)
#define IFSET(a, flag, cmd)