52template <
class IT,
class NT,
class DER>
55 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
58 perror(
"Input file doesn't exist\n");
65template <
class IT,
class NT,
class DER>
68 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
72template <
class IT,
class NT,
class DER>
75 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
79template <
class IT,
class NT,
class DER>
82 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
88template <
class IT,
class NT,
class DER>
91 SpParHelper::Print(
"COMBBLAS Warning: It is dangerous to create (matrix) objects without specifying the communicator, are you sure you want to create this object in MPI_COMM_WORLD?\n");
92 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
100template <
class IT,
class NT,
class DER>
104 assert( (
sizeof(
IT) >=
sizeof(
typename DER::LocalIT)) );
109template <
class IT,
class NT,
class DER>
112 if(spSeq !=
NULL)
delete spSeq;
115template <
class IT,
class NT,
class DER>
118 if(spSeq !=
NULL)
delete spSeq;
128template <
class IT,
class NT,
class DER>
129template <
typename VT,
typename GIT>
150 for(
int k = 0; k<colneighs; ++k)
155 for(
int k = 0; k<colneighs; ++k)
178#pragma omp parallel for
201 for (
int i=0; i<nprocs; i++)
212#pragma omp parallel for
217 int myThread = omp_get_thread_num();
263 IT n_perproc = getlocalcols() / colneighs;
289#pragma omp parallel for
296 for (
int i=0; i<nprocs; i++)
307template <
class IT,
class NT,
class DER>
308template <
typename VT,
typename GIT>
321 int colneighs =
commGrid->GetGridRows();
333 MPI_Sendrecv(&
xsize, 1,
MPI_INT, diagneigh,
TRX, &
trxsize, 1,
MPI_INT, diagneigh,
TRX,
commGrid->GetWorld(), &
status);
336 MPI_Sendrecv(
const_cast<IT*
>(
SpHelper::p2a(
colcnt.arr)),
xsize,
MPIType<IT>(), diagneigh,
TRX,
trxnums,
trxsize,
MPIType<IT>(), diagneigh,
TRX,
commGrid->GetWorld(), &
status);
338 int *
colsize =
new int[colneighs];
341 int *
dpls =
new int[colneighs]();
354 if(
accsize !=
locm) std::cout <<
"Gather vector along columns logic is wrong" << std::endl;
357 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
374 if(myrank == 0) std::cout <<
"Number of initial active columns are " <<
totactcols << std::endl;
377 if(myrank == 0) std::cout <<
"Number of initial nonzeros are " <<
totactnnzs << std::endl;
381 if(myrank == 0) std::cout <<
"Number of initial active columns are " <<
glactcols << std::endl;
382 if(
glactcols !=
totactcols)
if(myrank == 0) std::cout <<
"Wrong number of active columns are computed" << std::endl;
390 rvec.PrintInfo(
"rvector");
395 std::ostringstream
ss;
396 ss <<
"TopK: k_limit (" <<
k_limit <<
")" <<
" >= maxNnzInColumn. Returning the result of Reduce(Column, minimum<NT>()) instead..." << std::endl;
403 for (
IT i=0,
j=0; i<
locm; ++i) {
425 int *
sendcnt =
new int[nprocs];
426 int *
recvcnt =
new int[nprocs];
427 int *
sdispls =
new int[nprocs]();
428 int *
rdispls =
new int[nprocs]();
452#pragma omp parallel for
478 if(myrank == 0) std::cout <<
"Number of active nonzeros are " <<
totactnnzs << std::endl;
487 std::vector< std::vector< std::pair<IT,NT> > >
tmppair(nprocs);
490 TopKGather(
all_medians,
nnz_per_col,
chunksize,
chunksize,
activemedians,
activennzperc, i,
localmat,
actcolsmap,
klimits,
toretain,
tmppair,
coffset,
rvec);
492 TopKGather(
all_medians,
nnz_per_col,
lastchunk,
chunksize,
activemedians,
activennzperc,
iterations-1,
localmat,
actcolsmap,
klimits,
toretain,
tmppair,
coffset,
rvec);
496 for(
IT i=0; i<nprocs; ++i)
511 for(
int i=0; i<nprocs; ++i)
514 std::vector< std::pair<IT,NT> >().
swap(
tmppair[i]);
528 if(myrank == 0) std::cout <<
"Total vector entries updated " <<
updated << std::endl;
547 if(myrank == 0) std::cout <<
"Number of active columns are " <<
totactcols << std::endl;
554 if(myrank == 0) std::cout <<
"Exiting kselect2"<< std::endl;
561template <
class IT,
class NT,
class DER>
575 int colneighs =
commGrid->GetGridRows();
602 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
618template <
class IT,
class NT,
class DER>
622 spSeq =
new DER(*(
rhs.spSeq));
627template <
class IT,
class NT,
class DER>
634 if(spSeq !=
NULL)
delete spSeq;
636 spSeq =
new DER(*(
rhs.spSeq));
643template <
class IT,
class NT,
class DER>
650 (*spSeq) += (*(
rhs.spSeq));
654 std::cout <<
"Grids are not comparable for parallel addition (A+B)" << std::endl;
659 std::cout<<
"Missing feature (A+A): Use multiply with 2 instead !"<<std::endl;
664template <
class IT,
class NT,
class DER>
675template <
class IT,
class NT,
class DER>
684template <
class IT,
class NT,
class DER>
693template <
class IT,
class NT,
class DER>
702template <
class IT,
class NT,
class DER>
703template <
typename _BinaryOperation>
709 std::cout <<
"Grids are not comparable for SpParMat::DimApply" << std::endl;
722 int diagneigh =
x.
commGrid->GetComplementRank();
724 MPI_Sendrecv(&
xsize, 1,
MPI_INT, diagneigh,
TRX, &
trxsize, 1,
MPI_INT, diagneigh,
TRX,
World, &
status);
727 MPI_Sendrecv(
const_cast<NT*
>(
SpHelper::p2a(
x.arr)),
xsize,
MPIType<NT>(), diagneigh,
TRX,
trxnums,
trxsize,
MPIType<NT>(), diagneigh,
TRX,
World, &
status);
729 int colneighs, colrank;
732 int *
colsize =
new int[colneighs];
736 int *
dpls =
new int[colneighs]();
744 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
771 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
783 std::cout <<
"Unknown scaling dimension, returning..." << std::endl;
789template <
class IT,
class NT,
class DER>
790template <
typename _BinaryOperation,
typename _UnaryOperation >
808 std::cout <<
"Unknown reduction dimension, returning empty vector" << std::endl;
817template <
class IT,
class NT,
class DER>
818template <
typename _BinaryOperation>
836 std::cout <<
"Unknown reduction dimension, returning empty vector" << std::endl;
846template <
class IT,
class NT,
class DER>
847template <
typename VT,
typename GIT,
typename _BinaryOperation>
854template <
class IT,
class NT,
class DER>
855template <
typename VT,
typename GIT,
typename _BinaryOperation,
typename _UnaryOperation>
862template <
class IT,
class NT,
class DER>
863template <
typename VT,
typename GIT,
typename _BinaryOperation,
typename _UnaryOperation>
880 int colneighs =
commGrid->GetGridRows();
881 int colrank =
commGrid->GetRankInProcCol();
887 if(colrank == colneighs-1)
895 std::vector<VT>
trarr;
896 typename DER::SpColIter
colit = spSeq->begcol();
897 for(
int i=0; i< colneighs; ++i)
923 int diagneigh =
commGrid->GetComplementRank();
925 MPI_Sendrecv(&
trlen, 1,
MPIType<IT>(), diagneigh,
TRNNZ, &
reallen, 1,
MPIType<IT>(), diagneigh,
TRNNZ,
commGrid->GetWorld(), &
status);
928 MPI_Sendrecv(
SpHelper::p2a(
trarr),
trlen,
MPIType<VT>(), diagneigh,
TRX,
SpHelper::p2a(
rvec.arr),
reallen,
MPIType<VT>(), diagneigh,
TRX,
commGrid->GetWorld(), &
status);
929 rvec.glen = getncol();
935 rvec.glen = getnrow();
949 #define MAXCOLUMNBATCH 5 * 1024 * 1024
950 typename DER::SpColIter
begfinger = spSeq->begcol();
959 std::vector<typename DER::SpColIter::NzIter>
nziters;
998 catch (std::length_error&
le)
1000 std::cerr <<
"Length error: " <<
le.what() << std::endl;
1006 std::cout <<
"Unknown reduction dimension, returning empty vector" << std::endl;
1013#define KSELECTLIMIT 10000
1021template <
class IT,
class NT,
class DER>
1022template <
typename VT,
typename GIT>
1025#ifdef COMBBLAS_DEBUG
1035 test1.PrintToFile(
"test1");
1036 test2.PrintToFile(
"test2");
1061template <
class IT,
class NT,
class DER>
1062template <
typename VT,
typename GIT>
1065#ifdef COMBBLAS_DEBUG
1092template <
class IT,
class NT,
class DER>
1093template <
typename VT,
typename GIT,
typename _UnaryOperation>
1107 SpParHelper::Print(
"Kselect: k is greater then maxNnzInColumn. Calling Reduce instead...\n");
1125 if(spSeq->getnnz()>0)
1127 typename DER::SpColIter
colit = spSeq->begcol();
1132 if(i==
colit.colid())
1148 std::vector<VT>
localmat(spSeq->getnnz());
1152#pragma omp parallel for
1154 for(
IT i=0; i<nzc; i++)
1157 typename DER::SpColIter
colit = spSeq->begcol() + i;
1185 int colneighs =
commGrid->GetGridRows();
1186 int colrank =
commGrid->GetRankInProcCol();
1188 for(
int p=2; p <= colneighs; p*=2)
1191 if(colrank%p == p/2)
1198 else if(colrank%p == 0)
1210#pragma omp parallel for
1239#pragma omp parallel for
1252 int root =
commGrid->GetDiagOfProcCol();
1253 if(root==0 && colrank==0)
1256#pragma omp parallel for
1264 kthItem[i] = std::numeric_limits<VT>::min();
1267 else if(root>0 && colrank==0)
1270#pragma omp parallel for
1278 kthItem[i] = std::numeric_limits<VT>::min();
1282 else if(root>0 && colrank==root)
1288 std::vector <int>
dpls;
1291 int proccols =
commGrid->GetGridCols();
1296 dpls.resize(proccols,0);
1307 rvec.glen = getncol();
1313template <
class IT,
class NT,
class DER>
1314template <
typename VT,
typename GIT,
typename _UnaryOperation>
1339 int colneighs =
commGrid->GetGridRows();
1340 int colrank =
commGrid->GetRankInProcCol();
1366 for(
int i=0; i<
accnz ; i++)
1385 if(spSeq->getnnz()>0)
1387 typename DER::SpColIter
colit = spSeq->begcol();
1392 if(i==
colit.colid())
1415#pragma omp parallel for
1417 for(
IT i=0; i<nzc; i++)
1420 typename DER::SpColIter
colit = spSeq->begcol() + i;
1457 for(
int p=2; p <= colneighs; p*=2)
1460 if(colrank%p == p/2)
1467 else if(colrank%p == 0)
1479#pragma omp parallel for
1508#pragma omp parallel for
1537#pragma omp parallel for
1546 kthItem[i] = std::numeric_limits<VT>::min();
1579 int proccols =
commGrid->GetGridCols();
1580 std::vector <int>
sendcnts(proccols,0);
1581 std::vector <int>
dpls(proccols,0);
1597template <
class IT,
class NT,
class DER>
1602 IT m_perproc = getnrow() /
commGrid->GetGridRows();
1603 IT n_perproc = getncol() /
commGrid->GetGridCols();
1607 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
1610 typename DER::SpColIter::NzIter
nzit = spSeq->begnz(
colit);
1640template <
class IT,
class NT,
class DER>
1643 int colrank =
commGrid->GetRankInProcRow();
1661 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
1664 typename DER::SpColIter::NzIter
nzit = spSeq->begnz(
colit);
1702template <
class IT,
class NT,
class DER>
1703template <
typename VT,
typename GIT,
typename _BinaryOperation>
1723template <
class IT,
class NT,
class DER>
1724template <
typename VT,
typename GIT,
typename _BinaryOperation,
typename _UnaryOperation>
1725void SpParMat<IT,NT,DER>::MaskedReduce(
FullyDistVec<GIT,VT> &
rvec,
FullyDistSpVec<GIT,VT> &
mask,
Dim dim,
_BinaryOperation __binary_op,
VT id,
_UnaryOperation __unary_op,
bool exclude)
const
1760 int colneighs =
commGrid->GetGridRows();
1761 int colrank =
commGrid->GetRankInProcCol();
1767 if(colrank == colneighs-1)
1775 std::vector<VT>
trarr;
1776 typename DER::SpColIter
colit = spSeq->begcol();
1777 for(
int i=0; i< colneighs; ++i)
1785 typename DER::SpColIter::NzIter
nzit = spSeq->begnz(
colit);
1832 int diagneigh =
commGrid->GetComplementRank();
1834 MPI_Sendrecv(&
trlen, 1,
MPIType<IT>(), diagneigh,
TRNNZ, &
reallen, 1,
MPIType<IT>(), diagneigh,
TRNNZ,
commGrid->GetWorld(), &
status);
1837 MPI_Sendrecv(
SpHelper::p2a(
trarr),
trlen,
MPIType<VT>(), diagneigh,
TRX,
SpHelper::p2a(
rvec.arr),
reallen,
MPIType<VT>(), diagneigh,
TRX,
commGrid->GetWorld(), &
status);
1838 rvec.glen = getncol();
1845template <
class IT,
class NT,
class DER>
1846template <
typename NNT,
typename NDER>
1854template <
class IT,
class NT,
class DER>
1855template <
typename NIT,
typename NNT,
typename NDER>
1866template <
class IT,
class NT,
class DER>
1881template <
class IT,
class NT,
class DER>
1882template <
typename PTNTBOOL,
typename PTBOOLNT>
1898 locmax_ri = *std::max_element(
ri.arr.begin(),
ri.arr.end());
1900 locmax_ci = *std::max_element(
ci.arr.begin(),
ci.arr.end());
1930 IT diagneigh =
commGrid->GetComplementRank();
1935 MPI_Sendrecv(&
mylocalrows, 1,
MPIType<IT>(), diagneigh,
TRROWX, &
trlocalrows, 1,
MPIType<IT>(), diagneigh,
TRROWX,
commGrid->GetWorld(), &
status);
1938 std::vector< std::vector<IT> > rowid(
rowneighs);
1939 std::vector< std::vector<IT> > colid(
rowneighs);
1943 for(
typename std::vector<IT>::size_type i=0; i< (
unsigned)
locvec; ++i)
1973 std::vector<IT>().swap(rowid[i]);
1980 std::vector<IT>().swap(colid[i]);
1985 std::tuple<IT,IT,bool> *
p_tuples =
new std::tuple<IT,IT,bool>[
p_nnz];
2041 for(
typename std::vector<IT>::size_type i=0; i< (
unsigned)
locvec; ++i)
2068 std::vector<IT>().swap(rowid[i]);
2075 std::vector<IT>().swap(colid[i]);
2080 std::tuple<IT,IT,bool> *
q_tuples =
new std::tuple<IT,IT,bool>[
q_nnz];
2105template <
class IT,
class NT,
class DER>
2148template <
class IT,
class NT,
class DER>
2163 locmax_ri = *std::max_element(
ri.arr.begin(),
ri.arr.end());
2165 locmax_ci = *std::max_element(
ci.arr.begin(),
ci.arr.end());
2183template <
class IT,
class NT,
class DER>
2184template <
typename _BinaryOperation>
2188 if(getncol() !=
pvals.TotalLength())
2190 std::ostringstream
outs;
2191 outs <<
"Can not prune column-by-column, dimensions does not match"<< std::endl;
2192 outs << getncol() <<
" != " <<
pvals.TotalLength() << std::endl;
2196 if(! ( *(getcommgrid()) == *(
pvals.getcommgrid())) )
2198 std::cout <<
"Grids are not comparable for PurneColumn" << std::endl;
2211 MPI_Sendrecv(&
xsize, 1,
MPI_INT, diagneigh,
TRX, &
trxsize, 1,
MPI_INT, diagneigh,
TRX,
World, &
status);
2215 MPI_Sendrecv(
const_cast<NT*
>(
SpHelper::p2a(
pvals.arr)),
xsize,
MPIType<NT>(), diagneigh,
TRX,
trxnums,
trxsize,
MPIType<NT>(), diagneigh,
TRX,
World, &
status);
2217 int colneighs, colrank;
2220 int *
colsize =
new int[colneighs];
2223 int *
dpls =
new int[colneighs]();
2228#ifdef COMBBLAS_DEBUG
2229 std::ostringstream
outs2;
2230 outs2 <<
"PruneColumn displacements: ";
2231 for(
int i=0; i< colneighs; ++i)
2262template <
class IT,
class NT,
class DER>
2263template <
typename _BinaryOperation>
2267 if(getncol() !=
pvals.TotalLength())
2269 std::ostringstream
outs;
2270 outs <<
"Can not prune column-by-column, dimensions does not match"<< std::endl;
2271 outs << getncol() <<
" != " <<
pvals.TotalLength() << std::endl;
2275 if(! ( *(getcommgrid()) == *(
pvals.getcommgrid())) )
2277 std::cout <<
"Grids are not comparable for PurneColumn" << std::endl;
2291 MPI_Sendrecv(&
roffst, 1,
MPIType<IT>(), diagneigh,
TROST, &
roffset, 1,
MPIType<IT>(), diagneigh,
TROST,
World, &
status);
2292 MPI_Sendrecv(&
xlocnz, 1,
MPIType<IT>(), diagneigh,
TRNNZ, &
trxlocnz, 1,
MPIType<IT>(), diagneigh,
TRNNZ,
World, &
status);
2296 MPI_Sendrecv(
pvals.ind.data(),
xlocnz,
MPIType<IT>(), diagneigh,
TRI,
trxinds.data(),
trxlocnz,
MPIType<IT>(), diagneigh,
TRI,
World, &
status);
2297 MPI_Sendrecv(
pvals.num.data(),
xlocnz,
MPIType<NT>(), diagneigh,
TRX,
trxnums.data(),
trxlocnz,
MPIType<NT>(), diagneigh,
TRX,
World, &
status);
2301 int colneighs, colrank;
2304 int *
colnz =
new int[colneighs];
2307 int *
dpls =
new int[colneighs]();
2334template <
class IT,
class NT,
class DER>
2343 std::cout <<
"Grids are not comparable, EWiseMult() fails !" << std::endl;
2349template <
class IT,
class NT,
class DER>
2354 spSeq->EWiseScale(
rhs.array,
rhs.m,
rhs.n);
2358 std::cout <<
"Grids are not comparable, EWiseScale() fails !" << std::endl;
2363template <
class IT,
class NT,
class DER>
2364template <
typename _BinaryOperation>
2369 if(getlocalrows() ==
rhs.m && getlocalcols() ==
rhs.n)
2375 std::cout <<
"Matrices have different dimensions, UpdateDense() fails !" << std::endl;
2381 std::cout <<
"Grids are not comparable, UpdateDense() fails !" << std::endl;
2386template <
class IT,
class NT,
class DER>
2394 std::cout <<
"As a whole: " <<
mm <<
" rows and "<<
nn <<
" columns and "<<
nznz <<
" nonzeros" << std::endl;
2402 std::cout <<
"Processor (" <<
commGrid->GetRankInProcRow() <<
"," <<
commGrid->GetRankInProcCol() <<
")'s data: " << std::endl;
2410template <
class IT,
class NT,
class DER>
2413 int local =
static_cast<int>((*spSeq) == (*(
rhs.spSeq)));
2416 return static_cast<bool>(
whole);
2424template <
class IT,
class NT,
class DER>
2425template <
typename _BinaryOperation,
typename LIT>
2429 int *
sendcnt =
new int[nprocs];
2430 int *
recvcnt =
new int[nprocs];
2431 for(
int i=0; i<nprocs; ++i)
2435 int *
sdispls =
new int[nprocs]();
2436 int *
rdispls =
new int[nprocs]();
2456 if(
commGrid->GetRank() == 0) { std::copy(
gsizes,
gsizes+nprocs, std::ostream_iterator<IT>(std::cout,
" ")); std::cout << std::endl; }
2464 std::tuple<LIT,LIT,NT> *
senddata =
new std::tuple<LIT,LIT,NT>[
locsize];
2465 for(
int i=0; i<nprocs; ++i)
2469 data[i].shrink_to_fit();
2475 std::tuple<LIT,LIT,NT> *
recvdata =
new std::tuple<LIT,LIT,NT>[
totrecv];
2485 int myprocrow =
commGrid->GetRankInProcCol();
2486 int myproccol =
commGrid->GetRankInProcRow();
2488 if(myprocrow !=
r-1)
locrows = m_perproc;
2490 if(myproccol != s-1)
loccols = n_perproc;
2496 A.RemoveDuplicates(
BinOp);
2498 spSeq =
new DER(
A,
false);
2503template <
class IT,
class NT,
class DER>
2520 std::vector< std::vector < std::tuple<IT,IT,NT> > > data(nprocs);
2541template <
class IT,
class NT,
class DER>
2557 std::vector< std::vector < std::tuple<IT,IT,NT> > > data(nprocs);
2576template <
class IT,
class NT,
class DER>
2577template <
class DELIT>
2581 typedef typename DER::LocalIT
LIT;
2586 std::vector< std::vector<LIT> > data(nprocs);
2593 std::ostringstream
outs;
2594 outs <<
"Warning: Using smaller indices for the matrix than DistEdgeList\n";
2595 outs <<
"Local matrices are " << m_perproc <<
"-by-" << n_perproc << std::endl;
2619 int64_t to = get_v1_from_edge(&(
DEL.pedges[i]));
2621 if(
fr >= 0 && to >= 0)
2635 if(
DEL.edges[2*i+0] >= 0 &&
DEL.edges[2*i+1] >= 0)
2647 int *
sendcnt =
new int[nprocs];
2648 int *
sdispls =
new int[nprocs];
2649 for(
int i=0; i<nprocs; ++i)
2652 int *
rdispls =
new int[nprocs];
2653 int *
recvcnt =
new int[nprocs];
2658 for(
int i=0; i<nprocs-1; ++i)
2663 for(
int i=0; i<nprocs; ++i)
2667 for(
int i=0; i<nprocs; ++i)
2668 std::vector<LIT>().swap(data[i]);
2682 int myprocrow =
commGrid->GetRankInProcCol();
2683 int myproccol =
commGrid->GetRankInProcRow();
2691 spSeq =
new DER(
A,
false);
2694template <
class IT,
class NT,
class DER>
2704 removed = tuples.RemoveLoops();
2705 spSeq =
new DER(tuples,
false);
2713template <
class IT,
class NT,
class DER>
2719 typedef typename DER::LocalIT
LIT;
2723 tuples.SortColBased();
2724 spSeq =
new DER(tuples,
false);
2730template <
class IT,
class NT,
class DER>
2740 if (getncol()!=
loopvals.TotalLength())
2742 SpParHelper::Print(
"The number of entries in loopvals is not equal to the number of diagonal entries.\n");
2765 typedef typename DER::LocalIT
LIT;
2769 tuples.SortColBased();
2770 spSeq =
new DER(tuples,
false);
2778template <
class IT,
class NT,
class DER>
2779template <
typename LIT,
typename OT>
2782 if(spSeq->getnsplit() > 0)
2788 typedef typename DER::LocalIT
LocIT;
2817 int diagneigh =
commGrid->GetComplementRank();
2818 MPI_Sendrecv(&
offset, 1,
MPIType<IT>(), diagneigh,
TRTAGNZ, &
diagoffset, 1,
MPIType<IT>(), diagneigh,
TRTAGNZ,
commGrid->GetWorld(), &
status);
2843 for(
int i=0; i<
p_r; ++i)
2860 std::vector<bool> isthere(
mA,
false);
2861 std::vector<int>
maxlens(p_c,0);
2863 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
2872 isthere[rowid] =
true;
2880template <
class IT,
class NT,
class DER>
2891template <
class IT,
class NT,
class DER>
2892template <
typename SR>
2898 typedef typename DER::LocalIT
LIT;
2916 std::vector< SpTuples<LIT,NT> *>
tomerge;
2921 for(
int i = 0; i <
stages; ++i)
2923 std::vector<LIT>
ess;
2927 ess.resize(DER::esscount);
2928 for(
int j=0;
j< DER::esscount; ++
j)
2939 ess.resize(DER::esscount);
2940 for(
int j=0;
j< DER::esscount; ++
j)
2959 for(
unsigned int i=0; i<
tomerge.size(); ++i)
2964template <
class IT,
class NT,
class DER>
2973 typedef typename DER::LocalIT
LIT;
2991 int diagneigh =
commGrid->GetComplementRank();
2994 MPI_Sendrecv(&
locnnz, 1,
MPIType<LIT>(), diagneigh,
TRTAGNZ, &
remotennz, 1,
MPIType<LIT>(), diagneigh,
TRTAGNZ,
commGrid->GetWorld(), &
status);
2995 MPI_Sendrecv(&
locn, 1,
MPIType<LIT>(), diagneigh,
TRTAGM, &
remotem, 1,
MPIType<LIT>(), diagneigh,
TRTAGM,
commGrid->GetWorld(), &
status);
2996 MPI_Sendrecv(&
locm, 1,
MPIType<LIT>(), diagneigh,
TRTAGN, &
remoten, 1,
MPIType<LIT>(), diagneigh,
TRTAGN,
commGrid->GetWorld(), &
status);
2999 MPI_Sendrecv(
rows,
locnnz,
MPIType<LIT>(), diagneigh,
TRTAGROWS,
rowsrecv,
remotennz,
MPIType<LIT>(), diagneigh,
TRTAGROWS,
commGrid->GetWorld(), &
status);
3003 MPI_Sendrecv(
cols,
locnnz,
MPIType<LIT>(), diagneigh,
TRTAGCOLS,
colsrecv,
remotennz,
MPIType<LIT>(), diagneigh,
TRTAGCOLS,
commGrid->GetWorld(), &
status);
3007 MPI_Sendrecv(
vals,
locnnz,
MPIType<NT>(), diagneigh,
TRTAGVALS,
valsrecv,
remotennz,
MPIType<NT>(), diagneigh,
TRTAGVALS,
commGrid->GetWorld(), &
status);
3025template <
class IT,
class NT,
class DER>
3026template <
class HANDLER>
3029 int proccols =
commGrid->GetGridCols();
3030 int procrows =
commGrid->GetGridRows();
3039 std::stringstream
strm;
3040 strm <<
"%%MatrixMarket matrix coordinate real general" << std::endl;
3048 int colrank =
commGrid->GetRankInProcCol();
3049 int colneighs =
commGrid->GetGridRows();
3060 for(
int i = 0; i < procrows; i++)
3062 if(
commGrid->GetRankInProcCol() == i)
3065 std::vector< std::vector< std::pair<IT,NT> > >
csr(
localrows);
3066 if(
commGrid->GetRankInProcRow() == 0)
3070 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
3074 csr[
nzit.rowid()].push_back( std::make_pair(
colit.colid(),
nzit.value()) );
3083 for(
typename DER::SpColIter
colit = spSeq->begcol();
colit != spSeq->endcol(); ++
colit)
3093 if(
commGrid->GetRankInProcRow() == 0)
3096 gsizes =
new int[proccols];
3097 dpls =
new int[proccols]();
3102 sort(
csr[
j].begin(),
csr[
j].end());
3105 if(
commGrid->GetRankInProcRow() == 0)
3115 if(
commGrid->GetRankInProcRow() == 0)
3117 for(
int k=0; k<
rowcnt; ++k)
3132 if(
commGrid->GetRankInProcRow() == 0)
3145template <
class IT,
class NT,
class DER>
3161 std::cout <<
"File is " <<
file_size <<
" bytes" << std::endl;
3171 typedef std::map<std::string, uint64_t>
KEYMAP;
3172 std::vector< KEYMAP >
allkeys(nprocs);
3174 std::vector<std::string>
lines;
3188#ifdef COMBBLAS_DEBUG
3190 std::cout <<
"Initial reading finished. Total number of entries read across all processors is " <<
allentriesread << std::endl;
3193 int *
sendcnt =
new int[nprocs];
3194 int *
recvcnt =
new int[nprocs];
3195 for(
int i=0; i<nprocs; ++i)
3199 int *
sdispls =
new int[nprocs]();
3200 int *
rdispls =
new int[nprocs]();
3214 #pragma omp parallel for
3215 for(
int i=0; i<nprocs; ++i)
3221 std::array<char, MAXVERTNAME>
vname;
3222 std::copy(
pobj.first.begin(),
pobj.first.end(),
vname.begin() );
3239 std::set< std::pair<uint64_t, std::string> >
uniqsorted;
3249#ifdef COMBBLAS_DEBUG
3251 std::cout <<
"out of " <<
totrecv <<
" vertices received, " <<
uniqsize <<
" were unique" << std::endl;
3264 std::vector< std::vector< IT > >
locs_send(nprocs);
3265 std::vector< std::vector< std::string > >
data_send(nprocs);
3266 int *
map_scnt =
new int[nprocs]();
3301 std::cout <<
"Assertion failed at proc " << myrank <<
": the absence of the entry in invindex is unexpected!!!" << std::endl;
3317template <
class IT,
class NT,
class DER>
3318template <
typename _BinaryOperation>
3330 typedef std::map<std::string, uint64_t>
KEYMAP;
3341 std::cout <<
"the duplication in ultimateperm is unexpected!!!" << std::endl;
3360 typedef typename DER::LocalIT
LIT;
3361 std::vector<LIT>
rows;
3362 std::vector<LIT>
cols;
3363 std::vector<NT>
vals;
3365 std::vector<std::string>
lines;
3379#ifdef COMBBLAS_DEBUG
3381 std::cout <<
"Second reading finished. Total number of entries read across all processors is " <<
allentriesread << std::endl;
3385 std::vector< std::vector < std::tuple<LIT,LIT,NT> > > data(nprocs);
3394 std::vector<LIT>().swap(
rows);
3395 std::vector<LIT>().swap(
cols);
3396 std::vector<NT>().swap(
vals);
3398#ifdef COMBBLAS_DEBUG
3400 std::cout <<
"Packing to recipients finished, about to send..." << std::endl;
3403 if(spSeq)
delete spSeq;
3415template <
class IT,
class NT,
class DER>
3416template <
typename _BinaryOperation>
3432 printf(
"COMBBLAS: Matrix-market file %s can not be found\n",
filename.c_str());
3437 printf(
"Could not process Matrix Market banner.\n");
3444 printf(
"Sorry, this application does not support complext types");
3449 std::cout <<
"Matrix is Float" << std::endl;
3454 std::cout <<
"Matrix is Integer" << std::endl;
3459 std::cout <<
"Matrix is Boolean" << std::endl;
3464 std::cout <<
"Matrix is symmetric" << std::endl;
3471 std::cout <<
"Total number of nonzeros expected across all processors is " <<
nonzeros << std::endl;
3490 std::cout <<
"File is " <<
file_size <<
" bytes" << std::endl;
3508 typedef typename DER::LocalIT
LIT;
3509 std::vector<LIT>
rows;
3510 std::vector<LIT>
cols;
3511 std::vector<NT>
vals;
3513 std::vector<std::string>
lines;
3527#ifdef COMBBLAS_DEBUG
3529 std::cout <<
"Reading finished. Total number of entries read across all processors is " <<
allentriesread << std::endl;
3532 std::vector< std::vector < std::tuple<LIT,LIT,NT> > > data(nprocs);
3541 std::vector<LIT>().swap(
rows);
3542 std::vector<LIT>().swap(
cols);
3543 std::vector<NT>().swap(
vals);
3545#ifdef COMBBLAS_DEBUG
3547 std::cout <<
"Packing to recepients finished, about to send..." << std::endl;
3550 if(spSeq)
delete spSeq;
3558template <
class IT,
class NT,
class DER>
3559template <
class HANDLER>
3578 IT m_perproc = 0, n_perproc = 0;
3580 int colneighs =
commGrid->GetGridRows();
3602 SpParHelper::Print(
"COMBBLAS: MPI doesn't support sending int64_t send/recv counts or displacements\n",
commGrid->GetWorld());
3605 int *
cdispls =
new int[colneighs];
3619 std::vector< std::tuple<IT, IT, NT> >
localtuples;
3623 if( !
hfile.fileexists )
3637 if ( !
hfile.headerexists )
3646 std::stringstream
ss;
3663 m_perproc =
total_m / colneighs;
3677 ReadAllMine(
binfile,
rows,
cols,
vals,
localtuples,
rcurptrs,
ccurptrs,
rdispls,
cdispls, m_perproc, n_perproc,
3720 colrec = std::min(
static_cast<int>(
temprow / m_perproc), colneighs-1);
3748 std::fill_n(
ccurptrs, colneighs, 0);
3766 std::fill_n(
ccurptrs, colneighs, std::numeric_limits<int>::max());
3777 m_perproc =
total_m / colneighs;
3800 ReadAllMine(
binfile,
rows,
cols,
vals,
localtuples,
rcurptrs,
ccurptrs,
rdispls,
cdispls, m_perproc, n_perproc,
3816 if(
recvcount == std::numeric_limits<int>::max())
break;
3846 m_perproc =
total_m / colneighs;
3852 if(
recvcount == std::numeric_limits<int>::max())
3889template <
class IT,
class NT,
class DER>
3899 std::fill_n(
ccurptrs, colneighs, 0);
3903template <
class IT,
class NT,
class DER>
3904void SpParMat<IT,NT,DER>::BcastEssentials(MPI_Comm & world, IT & total_m, IT & total_n, IT & total_nnz,
int master)
3915template <
class IT,
class NT,
class DER>
3916void SpParMat<IT,NT,DER>::VerticalSend(IT * & rows, IT * & cols, NT * & vals, std::vector< std::tuple<IT,IT,NT> > & localtuples,
int * rcurptrs,
int * ccurptrs,
int * rdispls,
int * cdispls,
3917 IT m_perproc, IT n_perproc,
int rowneighs,
int colneighs, IT buffperrowneigh, IT buffpercolneigh,
int rankinrow)
3925 for(
int i=0; i<colneighs-1; ++i)
3939 std::fill_n(
ccurptrs, colneighs, 0);
3944 HorizontalSend(
rows,
cols,
vals,
temprows,
tempcols,
tempvals,
localtuples,
rcurptrs,
rdispls,
buffperrowneigh,
rowneighs,
totrecv, m_perproc, n_perproc,
rankinrow);
3959template <
class IT,
class NT,
class DER>
3960template <
class HANDLER>
3961void SpParMat<IT,NT,DER>::ReadAllMine(FILE * binfile, IT * & rows, IT * & cols, NT * & vals, std::vector< std::tuple<IT,IT,NT> > & localtuples,
int * rcurptrs,
int * ccurptrs,
int * rdispls,
int * cdispls,
3962 IT m_perproc, IT n_perproc,
int rowneighs,
int colneighs, IT buffperrowneigh, IT buffpercolneigh, IT entriestoread, HANDLER handler,
int rankinrow,
bool transpose)
3978 int colrec = std::min(
static_cast<int>(
temprow / m_perproc), colneighs-1);
3989 oput <<
"To column neighbors: ";
3994 VerticalSend(
rows,
cols,
vals,
localtuples,
rcurptrs,
ccurptrs,
rdispls,
cdispls, m_perproc, n_perproc,
4006 oput <<
"To column neighbors: ";
4013 VerticalSend(
rows,
cols,
vals,
localtuples,
rcurptrs,
ccurptrs,
rdispls,
cdispls, m_perproc, n_perproc,
4041template <
class IT,
class NT,
class DER>
4042void SpParMat<IT,NT,DER>::HorizontalSend(IT * & rows, IT * & cols, NT * & vals, IT * & temprows, IT * & tempcols, NT * & tempvals, std::vector < std::tuple <IT,IT,NT> > & localtuples,
4043 int * rcurptrs,
int * rdispls, IT buffperrowneigh,
int rowneighs,
int recvcount, IT m_perproc, IT n_perproc,
int rankinrow)
4062 oput <<
"To row neighbors: ";
4064 oput <<
"Row displacements were: ";
4099template <
class IT,
class NT,
class DER>
4124 int *
sendcnt =
new int[nprocs]();
4130 int colrank =
commGrid->GetRankInProcCol();
4132 int colneighs =
commGrid->GetGridRows();
4135 locnrows[colrank] = getlocalrows();
4145 for(
int i=0; i<
prelen; ++i)
4156 int *
recvcnt =
new int[nprocs];
4159 int *
sdpls =
new int[nprocs]();
4160 int *
rdpls =
new int[nprocs]();
4177template <
class IT,
class NT,
class DER>
4200 int *
sendcnt =
new int[nprocs]();
4206 int colrank =
commGrid->GetRankInProcCol();
4208 int colneighs =
commGrid->GetGridRows();
4211 locnrows[colrank] = getlocalrows();
4220 for(
int i=0; i<
prelen; ++i)
4230 int *
recvcnt =
new int[nprocs];
4233 int *
sdpls =
new int[nprocs]();
4234 int *
rdpls =
new int[nprocs]();
4247template <
class IT,
class NT,
class DER>
4250 outfile << (*spSeq) << std::endl;
4254template <
class IU,
class NU,
class UDER>
4268template <
class IT,
class NT,
class DER>
4269template <
typename LIT>
4272 int procrows =
commGrid->GetGridRows();
4273 int proccols =
commGrid->GetGridCols();
4280 own_procrow = std::min(
static_cast<int>(
grow / m_perproc), procrows-1);
4289 own_proccol = std::min(
static_cast<int>(
gcol / n_perproc), proccols-1);
4304template <
class IT,
class NT,
class DER>
4310 int procrows =
commGrid->GetGridRows();
4311 int proccols =
commGrid->GetGridCols();
std::shared_ptr< CommGrid > commGrid
int64_t getGlobalV() const
static void ProcessLines(std::vector< IT1 > &rows, std::vector< IT1 > &cols, std::vector< NT1 > &vals, std::vector< std::string > &lines, int symmetric, int type, bool onebased=true)
static void ProcessLinesWithStringKeys(std::vector< std::map< std::string, uint64_t > > &allkeys, std::vector< std::string > &lines, int nprocs)
static void deallocate2D(T **array, I m)
static void ProcessStrLinesNPermute(std::vector< IT1 > &rows, std::vector< IT1 > &cols, std::vector< NT1 > &vals, std::vector< std::string > &lines, std::map< std::string, uint64_t > &ultperm)
static const T * p2a(const std::vector< T > &v)
static bool FetchBatch(MPI_File &infile, MPI_Offset &curpos, MPI_Offset end_fpos, bool firstcall, std::vector< std::string > &lines, int myrank)
static void GetSetSizes(const SpMat< IT, NT, DER > &Matrix, IT **&sizes, MPI_Comm &comm1d)
static void BCastMatrix(MPI_Comm &comm1d, SpMat< IT, NT, DER > &Matrix, const std::vector< IT > &essentials, int root)
static void Print(const std::string &s)
static void ReDistributeToVector(int *&map_scnt, std::vector< std::vector< IT > > &locs_send, std::vector< std::vector< std::string > > &data_send, std::vector< std::array< char, MAXVERTNAME > > &distmapper_array, const MPI_Comm &comm)
bool Kselect2(FullyDistVec< GIT, VT > &rvec, IT k_limit) const
void EWiseScale(const DenseParMat< IT, NT > &rhs)
FullyDistVec< IT, std::array< char, MAXVERTNAME > > ReadGeneralizedTuples(const std::string &, _BinaryOperation)
void DimApply(Dim dim, const FullyDistVec< IT, NT > &v, _BinaryOperation __binary_op)
FullyDistVec< IT, NT > Reduce(Dim dim, _BinaryOperation __binary_op, NT id, _UnaryOperation __unary_op) const
SpParMat< IT, NT, DER > SubsRefCol(const std::vector< IT > &ci) const
Column indexing with special parallel semantics.
bool operator==(const SpParMat< IT, NT, DER > &rhs) const
void ReadDistribute(const std::string &filename, int master, bool nonum, HANDLER handler, bool transpose=false, bool pario=false)
bool Kselect(FullyDistVec< GIT, VT > &rvec, IT k_limit, int kselectVersion) const
void MaskedReduce(FullyDistVec< GIT, VT > &rvec, FullyDistSpVec< GIT, VT > &mask, Dim dim, _BinaryOperation __binary_op, VT id, bool exclude=false) const
SpParMat< IT, NT, DER > Prune(_UnaryOperation __unary_op, bool inPlace=true)
void ActivateThreading(int numsplits)
void Find(FullyDistVec< IT, IT > &, FullyDistVec< IT, IT > &, FullyDistVec< IT, NT > &) const
float LoadImbalance() const
SpParMat< IT, NT, DER > SubsRef_SR(const FullyDistVec< IT, IT > &ri, const FullyDistVec< IT, IT > &ci, bool inplace=false)
General indexing with serial semantics.
void SpAsgn(const FullyDistVec< IT, IT > &ri, const FullyDistVec< IT, IT > &ci, SpParMat< IT, NT, DER > &B)
SpParMat< IT, NT, DER > & operator+=(const SpParMat< IT, NT, DER > &rhs)
void Dump(std::string filename) const
void UpdateDense(DenseParMat< IT, NT > &rhs, _BinaryOperation __binary_op) const
friend SpParMat< IU, typename promote_trait< NU1, NU2 >::T_promote, typename promote_trait< UDER1, UDER2 >::T_promote > EWiseMult(const SpParMat< IU, NU1, UDER1 > &A, const SpParMat< IU, NU2, UDER2 > &B, bool exclude)
void AddLoops(NT loopval, bool replaceExisting=false)
void SaveGathered(std::string filename, HANDLER handler, bool transpose=false) const
SpParMat< IT, NT, DER > & operator=(const SpParMat< IT, NT, DER > &rhs)
void ParallelReadMM(const std::string &filename, bool onebased, _BinaryOperation BinOp)
bool Kselect1(FullyDistVec< GIT, VT > &rvec, IT k_limit, _UnaryOperation __unary_op) const
void OptimizeForGraph500(OptBuf< LIT, OT > &optbuf)
std::ofstream & put(std::ofstream &outfile) const
SpParMat()
Deprecated. Don't call the default constructor.
int Owner(IT total_m, IT total_n, IT grow, IT gcol, LIT &lrow, LIT &lcol) const
SpParMat< IT, NT, DER > PruneColumn(const FullyDistVec< IT, NT > &pvals, _BinaryOperation __binary_op, bool inPlace=true)
Prune every column of a sparse matrix based on pvals.
void SparseCommon(std::vector< std::vector< std::tuple< LIT, LIT, NT > > > &data, LIT locsize, IT total_m, IT total_n, _BinaryOperation BinOp)
#define MEM_EFFICIENT_STAGES
#define mm_is_complex(typecode)
#define mm_is_hermitian(typecode)
char * mm_typecode_to_str(MM_typecode matcode)
#define mm_is_real(typecode)
#define mm_is_pattern(typecode)
#define mm_is_integer(typecode)
int mm_read_mtx_crd_size(FILE *f, int64_t *M, int64_t *N, int64_t *nz, int64_t *numlinesread)
int mm_read_banner(FILE *f, MM_typecode *matcode)
#define mm_is_symmetric(typecode)
HeaderInfo ParseHeader(const std::string &inputname, FILE *&f, int &seeklength)
MPI_Datatype MPIType< double >(void)
std::ofstream & operator<<(std::ofstream &outfile, const SpMat< UIT, UNT, UDER > &s)
MPI_Datatype MPIType< int64_t >(void)
void AllGatherVector(MPI_Comm &ColWorld, int trxlocnz, IU lenuntil, int32_t *&trxinds, NV *&trxnums, int32_t *&indacc, NV *&numacc, int &accnz, bool indexisvalue)
void TransposeVector(MPI_Comm &World, const FullyDistSpVec< IU, NV > &x, int32_t &trxlocnz, IU &lenuntil, int32_t *&trxinds, NV *&trxnums, bool indexisvalue)
MPI_Datatype MPIType< uint64_t >(void)
Dcsc< IU, typename promote_trait< NU1, NU2 >::T_promote > EWiseMult(const Dcsc< IU, NU1 > &A, const Dcsc< IU, NU2 > *B, bool exclude)
shared_ptr< CommGrid > ProductGrid(CommGrid *gridA, CommGrid *gridB, int &innerdim, int &Aoffset, int &Boffset)
Collection of Generic Sequential Functions.
unsigned __int64 uint64_t