14 #define UNMATCHEDFOR2HOP 0.10 29 for (eqewgts=1, i=1; i<graph->
nedges; i++) {
37 for (i=0; i<graph->
ncon; i++)
49 switch (ctrl->
ctype) {
54 if (eqewgts || graph->
nedges == 0)
69 }
while (
graph->nvtxs > ctrl->CoarsenTo &&
92 for (eqewgts=1, i=1; i<graph->
nedges; i++) {
100 for (i=0; i<graph->
ncon; i++)
103 for (level=0; level<nlevels; level++) {
112 switch (ctrl->
ctype) {
117 if (eqewgts || graph->
nedges == 0)
151 idx_t i, pi, ii,
j, jj, jjinc, k, nvtxs,
ncon, cnvtxs, maxidx, last_unmatched;
160 nvtxs = graph->
nvtxs;
175 for (cnvtxs=0, last_unmatched=0, pi=0; pi<nvtxs; pi++) {
181 if ((ncon == 1 ? vwgt[i] < maxvwgt[0] :
ivecle(ncon, vwgt+i*ncon, maxvwgt))) {
184 if (xadj[i] == xadj[i+1]) {
185 last_unmatched =
gk_max(pi, last_unmatched)+1;
186 for (; last_unmatched<nvtxs; last_unmatched++) {
187 j = perm[last_unmatched];
198 for (j=xadj[i]; j<xadj[i+1]; j++) {
200 if (match[k] ==
UNMATCHED && vwgt[i]+vwgt[k] <= maxvwgt[0]) {
207 if (maxidx == i && 3*vwgt[i] < maxvwgt[0]) {
214 for (j=xadj[i]; j<xadj[i+1]; j++) {
217 ivecaxpylez(ncon, 1, vwgt+i*ncon, vwgt+k*ncon, maxvwgt)) {
224 if (maxidx == i &&
ivecaxpylez(ncon, 2, vwgt+i*ncon, vwgt+i*ncon, maxvwgt)) {
233 cmap[
i] = cmap[maxidx] = cnvtxs++;
244 cnvtxs =
Match_2Hop(ctrl, graph, perm, match, cnvtxs, nunmatched);
249 for (cnvtxs=0, i=0; i<nvtxs; i++) {
256 cmap[
i] = cmap[match[
i]] = cnvtxs++;
278 idx_t i, pi, ii,
j, jj, jjinc, k, nvtxs,
ncon, cnvtxs, maxidx, maxwgt,
279 last_unmatched, avgdegree;
288 nvtxs = graph->
nvtxs;
305 avgdegree = 0.7*(xadj[nvtxs]/nvtxs);
306 for (i=0; i<nvtxs; i++)
307 degrees[i] = (xadj[i+1]-xadj[i] > avgdegree ? avgdegree : xadj[i+1]-xadj[i]);
310 for (cnvtxs=0, last_unmatched=0, pi=0; pi<nvtxs; pi++) {
317 if ((ncon == 1 ? vwgt[i] < maxvwgt[0] :
ivecle(ncon, vwgt+i*ncon, maxvwgt))) {
320 if (xadj[i] == xadj[i+1]) {
321 last_unmatched =
gk_max(pi, last_unmatched)+1;
322 for (; last_unmatched<nvtxs; last_unmatched++) {
323 j = perm[last_unmatched];
334 for (j=xadj[i]; j<xadj[i+1]; j++) {
337 maxwgt < adjwgt[j] && vwgt[i]+vwgt[k] <= maxvwgt[0]) {
344 if (maxidx == i && 3*vwgt[i] < maxvwgt[0]) {
351 for (j=xadj[i]; j<xadj[i+1]; j++) {
354 ivecaxpylez(ncon, 1, vwgt+i*ncon, vwgt+k*ncon, maxvwgt) &&
355 (maxwgt < adjwgt[j] ||
356 (maxwgt == adjwgt[j] &&
358 vwgt+maxidx*ncon, vwgt+k*ncon)))) {
365 if (maxidx == i &&
ivecaxpylez(ncon, 2, vwgt+i*ncon, vwgt+i*ncon, maxvwgt)) {
374 cmap[
i] = cmap[maxidx] = cnvtxs++;
385 cnvtxs =
Match_2Hop(ctrl, graph, perm, match, cnvtxs, nunmatched);
390 for (cnvtxs=0, i=0; i<nvtxs; i++) {
397 cmap[
i] = cmap[match[
i]] = cnvtxs++;
416 idx_t cnvtxs,
size_t nunmatched)
419 cnvtxs =
Match_2HopAny(ctrl, graph, perm, match, cnvtxs, &nunmatched, 2);
420 cnvtxs =
Match_2HopAll(ctrl, graph, perm, match, cnvtxs, &nunmatched, 64);
422 cnvtxs =
Match_2HopAny(ctrl, graph, perm, match, cnvtxs, &nunmatched, 3);
438 idx_t cnvtxs,
size_t *r_nunmatched,
size_t maxdegree)
440 idx_t i, pi, ii,
j, jj, k, nvtxs;
447 nvtxs = graph->
nvtxs;
452 nunmatched = *r_nunmatched;
459 for (i=0; i<nvtxs; i++) {
460 if (match[i] ==
UNMATCHED && xadj[i+1]-xadj[i] < maxdegree) {
461 for (j=xadj[i]; j<xadj[i+1]; j++)
468 for (pi=0; pi<nvtxs; pi++) {
470 if (match[i] ==
UNMATCHED && xadj[i+1]-xadj[i] < maxdegree) {
471 for (j=xadj[i]; j<xadj[i+1]; j++)
472 rowind[colptr[adjncy[j]]++] = i;
478 for (pi=0; pi<nvtxs; pi++) {
480 if (colptr[i+1]-colptr[i] < 2)
483 for (jj=colptr[i+1], j=colptr[i]; j<jj; j++) {
485 for (jj--; jj>
j; jj--) {
487 cmap[rowind[
j]] = cmap[rowind[jj]] = cnvtxs++;
488 match[rowind[
j]] = rowind[jj];
489 match[rowind[jj]] = rowind[
j];
503 *r_nunmatched = nunmatched;
517 idx_t cnvtxs,
size_t *r_nunmatched,
size_t maxdegree)
519 idx_t i, pi, pk, ii,
j, jj, k, nvtxs, mask, idegree;
523 size_t nunmatched, ncand;
527 nvtxs = graph->
nvtxs;
532 nunmatched = *r_nunmatched;
541 for (ncand=0, pi=0; pi<nvtxs; pi++) {
543 idegree = xadj[i+1]-xadj[
i];
544 if (match[i] ==
UNMATCHED && idegree > 1 && idegree < maxdegree) {
545 for (k=0, j=xadj[i]; j<xadj[i+1]; j++)
548 keys[ncand].key = (k%mask)*maxdegree + idegree;
555 for (pi=0; pi<ncand; pi++) {
560 for (j=xadj[i]; j<xadj[i+1]; j++)
563 for (pk=pi+1; pk<ncand; pk++) {
568 if (keys[pi].
key != keys[pk].
key)
570 if (xadj[i+1]-xadj[i] != xadj[k+1]-xadj[k])
573 for (jj=xadj[k]; jj<xadj[k+1]; jj++) {
574 if (mark[adjncy[jj]] != i)
577 if (jj == xadj[k+1]) {
578 cmap[
i] = cmap[k] = cnvtxs++;
592 *r_nunmatched = nunmatched;
608 for (i=0; i<graph->
ncon; i++)
609 printf(
" %8"PRIDX
":%8"PRIDX, ctrl->
maxvwgt[i], graph->
tvwgt[i]);
624 idx_t j, jj, k, kk,
l,
m, istart, iend, nvtxs, nedges,
ncon, cnedges,
627 idx_t *cmap, *htable;
628 idx_t *cxadj, *cvwgt, *cvsize, *cadjncy, *cadjwgt;
635 if (cnvtxs < 2*mask || graph->nedges/graph->
nvtxs > mask/20) {
640 nvtxs = graph->
nvtxs;
642 for (v=0; v<nvtxs; v++) {
643 if (xadj[v+1]-xadj[v] > (mask>>3)) {
656 vsize = graph->
vsize;
663 cxadj = cgraph->
xadj;
664 cvwgt = cgraph->
vwgt;
665 cvsize = cgraph->
vsize;
671 cxadj[0] = cnvtxs = cnedges = 0;
672 for (v=0; v<nvtxs; v++) {
673 if ((u = match[v]) < v)
676 ASSERT(cmap[v] == cnvtxs);
677 ASSERT(cmap[match[v]] == cnvtxs);
680 cvwgt[cnvtxs] = vwgt[
v];
682 icopy(ncon, vwgt+v*ncon, cvwgt+cnvtxs*ncon);
685 cvsize[cnvtxs] = vsize[
v];
691 for (j=istart; j<iend; j++) {
694 if ((m = htable[kk]) == -1) {
696 cadjwgt[nedges] = adjwgt[
j];
697 htable[kk] = nedges++;
699 else if (cadjncy[m] == k) {
700 cadjwgt[
m] += adjwgt[
j];
703 for (jj=0; jj<nedges; jj++) {
704 if (cadjncy[jj] == k) {
705 cadjwgt[jj] += adjwgt[
j];
711 cadjwgt[nedges++] = adjwgt[
j];
718 cvwgt[cnvtxs] += vwgt[u];
720 iaxpy(ncon, 1, vwgt+u*ncon, 1, cvwgt+cnvtxs*ncon, 1);
723 cvsize[cnvtxs] += vsize[u];
727 for (j=istart; j<iend; j++) {
730 if ((m = htable[kk]) == -1) {
732 cadjwgt[nedges] = adjwgt[
j];
733 htable[kk] = nedges++;
735 else if (cadjncy[m] == k) {
736 cadjwgt[
m] += adjwgt[
j];
739 for (jj=0; jj<nedges; jj++) {
740 if (cadjncy[jj] == k) {
741 cadjwgt[jj] += adjwgt[
j];
747 cadjwgt[nedges++] = adjwgt[
j];
753 jj = htable[cnvtxs&mask];
754 if (jj >= 0 && cadjncy[jj] != cnvtxs) {
755 for (jj=0; jj<nedges; jj++) {
756 if (cadjncy[jj] == cnvtxs)
761 if (jj >= 0 && jj < nedges && cadjncy[jj] == cnvtxs) {
762 cadjncy[jj] = cadjncy[--nedges];
763 cadjwgt[jj] = cadjwgt[nedges];
768 for (j=0; j<nedges; j++)
769 htable[cadjncy[j]&mask] = -1;
770 htable[cnvtxs&mask] = -1;
773 cxadj[++cnvtxs] = cnedges;
780 for (j=0; j<
ncon; j++) {
803 idx_t j, k,
m, istart, iend, nvtxs, nedges,
ncon, cnedges,
v, u, dovsize;
805 idx_t *cmap, *htable;
806 idx_t *cxadj, *cvwgt, *cvsize, *cadjncy, *cadjwgt;
815 nvtxs = graph->
nvtxs;
819 vsize = graph->
vsize;
827 cxadj = cgraph->
xadj;
828 cvwgt = cgraph->
vwgt;
829 cvsize = cgraph->
vsize;
835 cxadj[0] = cnvtxs = cnedges = 0;
836 for (v=0; v<nvtxs; v++) {
837 if ((u = match[v]) < v)
840 ASSERT(cmap[v] == cnvtxs);
841 ASSERT(cmap[match[v]] == cnvtxs);
844 cvwgt[cnvtxs] = vwgt[
v];
846 icopy(ncon, vwgt+v*ncon, cvwgt+cnvtxs*ncon);
849 cvsize[cnvtxs] = vsize[
v];
855 for (j=istart; j<iend; j++) {
857 if ((m = htable[k]) == -1) {
859 cadjwgt[nedges] = adjwgt[
j];
860 htable[k] = nedges++;
863 cadjwgt[
m] += adjwgt[
j];
869 cvwgt[cnvtxs] += vwgt[u];
871 iaxpy(ncon, 1, vwgt+u*ncon, 1, cvwgt+cnvtxs*ncon, 1);
874 cvsize[cnvtxs] += vsize[u];
878 for (j=istart; j<iend; j++) {
880 if ((m = htable[k]) == -1) {
882 cadjwgt[nedges] = adjwgt[
j];
883 htable[k] = nedges++;
886 cadjwgt[
m] += adjwgt[
j];
891 if ((j = htable[cnvtxs]) != -1) {
892 ASSERT(cadjncy[j] == cnvtxs);
893 cadjncy[
j] = cadjncy[--nedges];
894 cadjwgt[
j] = cadjwgt[nedges];
900 for (j=0; j<nedges; j++)
901 htable[cadjncy[j]] = -1;
904 cxadj[++cnvtxs] = cnedges;
911 for (j=0; j<
ncon; j++) {
935 idx_t i,
j, jj, k, kk,
l,
m, istart, iend, nvtxs, nedges,
ncon, cnedges,
938 idx_t *cmap, *htable;
939 idx_t *cxadj, *cvwgt, *cvsize, *cadjncy, *cadjwgt;
950 nvtxs = graph->
nvtxs;
954 vsize = graph->
vsize;
961 cxadj = cgraph->
xadj;
962 cvwgt = cgraph->
vwgt;
963 cvsize = cgraph->
vsize;
969 cxadj[0] = cnvtxs = cnedges = 0;
970 for (i=0; i<nvtxs; i++) {
972 if (cmap[v] != cnvtxs)
977 cvwgt[cnvtxs] = vwgt[
v];
979 icopy(ncon, vwgt+v*ncon, cvwgt+cnvtxs*ncon);
982 cvsize[cnvtxs] = vsize[
v];
988 for (j=istart; j<iend; j++) {
991 if ((m = htable[kk]) == -1) {
993 cadjwgt[nedges] = adjwgt[
j];
994 htable[kk] = nedges++;
996 else if (cadjncy[m] == k) {
997 cadjwgt[
m] += adjwgt[
j];
1000 for (jj=0; jj<nedges; jj++) {
1001 if (cadjncy[jj] == k) {
1002 cadjwgt[jj] += adjwgt[
j];
1007 cadjncy[nedges] = k;
1008 cadjwgt[nedges++] = adjwgt[
j];
1015 cvwgt[cnvtxs] += vwgt[u];
1017 iaxpy(ncon, 1, vwgt+u*ncon, 1, cvwgt+cnvtxs*ncon, 1);
1020 cvsize[cnvtxs] += vsize[u];
1024 for (j=istart; j<iend; j++) {
1025 k = cmap[adjncy[
j]];
1027 if ((m = htable[kk]) == -1) {
1028 cadjncy[nedges] = k;
1029 cadjwgt[nedges] = adjwgt[
j];
1030 htable[kk] = nedges++;
1032 else if (cadjncy[m] == k) {
1033 cadjwgt[
m] += adjwgt[
j];
1036 for (jj=0; jj<nedges; jj++) {
1037 if (cadjncy[jj] == k) {
1038 cadjwgt[jj] += adjwgt[
j];
1043 cadjncy[nedges] = k;
1044 cadjwgt[nedges++] = adjwgt[
j];
1050 jj = htable[cnvtxs&mask];
1051 if (jj >= 0 && cadjncy[jj] != cnvtxs) {
1052 for (jj=0; jj<nedges; jj++) {
1053 if (cadjncy[jj] == cnvtxs)
1057 if (jj >= 0 && cadjncy[jj] == cnvtxs) {
1058 cadjncy[jj] = cadjncy[--nedges];
1059 cadjwgt[jj] = cadjwgt[nedges];
1063 for (j=0; j<nedges; j++)
1064 htable[cadjncy[j]&mask] = -1;
1065 htable[cnvtxs&mask] = -1;
1068 cxadj[++cnvtxs] = cnedges;
1073 cgraph->
nedges = cnedges;
1075 for (i=0; i<
ncon; i++) {
1099 cgraph->
nvtxs = cnvtxs;
1107 cgraph->
xadj =
imalloc(cnvtxs+1,
"SetupCoarseGraph: xadj");
1110 cgraph->
vwgt =
imalloc(cgraph->
ncon*cnvtxs,
"SetupCoarseGraph: vwgt");
1115 cgraph->
vsize =
imalloc(cnvtxs,
"SetupCoarseGraph: vsize");
const gtsam::Symbol key('X', 0)
void CreateCoarseGraphPerm(ctrl_t *ctrl, graph_t *graph, idx_t cnvtxs, idx_t *match, idx_t *perm)
idx_t idx_t idx_t idx_t * vwgt
bool match(const T &xpr, std::string ref, std::string str_xpr="")
#define gk_startcputimer(tmr)
idx_t Match_RM(ctrl_t *ctrl, graph_t *graph)
graph_t * CoarsenGraphNlevels(ctrl_t *ctrl, graph_t *graph, idx_t nlevels)
#define irandArrayPermute
#define BucketSortKeysInc
for(size_t i=1;i< poses.size();++i)
#define gk_stopcputimer(tmr)
void PrintCGraphStats(ctrl_t *ctrl, graph_t *graph)
void gk_errexit(int signum, char *f_str,...)
void CreateCoarseGraphNoMask(ctrl_t *ctrl, graph_t *graph, idx_t cnvtxs, idx_t *match)
NonlinearFactorGraph graph
void ReAdjustMemory(ctrl_t *ctrl, graph_t *graph, graph_t *cgraph)
idx_t idx_t idx_t idx_t idx_t * vsize
#define ASSERT(expression)
static const Line3 l(Rot3(), 1, 1)
idx_t Match_2HopAny(ctrl_t *ctrl, graph_t *graph, idx_t *perm, idx_t *match, idx_t cnvtxs, size_t *r_nunmatched, size_t maxdegree)
Array< int, Dynamic, 1 > v
graph_t * SetupCoarseGraph(graph_t *graph, idx_t cnvtxs, idx_t dovsize)
idx_t idx_t idx_t idx_t idx_t * perm
idx_t Match_2HopAll(ctrl_t *ctrl, graph_t *graph, idx_t *perm, idx_t *match, idx_t cnvtxs, size_t *r_nunmatched, size_t maxdegree)
#define SHIFTCSR(i, n, a)
idx_t idx_t idx_t idx_t idx_t idx_t * adjwgt
void CreateCoarseGraph(ctrl_t *ctrl, graph_t *graph, idx_t cnvtxs, idx_t *match)
idx_t idx_t idx_t * adjncy
idx_t Match_2Hop(ctrl_t *ctrl, graph_t *graph, idx_t *perm, idx_t *match, idx_t cnvtxs, size_t nunmatched)
idx_t Match_SHEM(ctrl_t *ctrl, graph_t *graph)
#define IFSET(a, flag, cmd)
graph_t * CoarsenGraph(ctrl_t *ctrl, graph_t *graph)