int bY(const int iD, int *piF){ //Y -> A.A int bSucces, iM, iF; bSucces = bA(iD,&iM) && bA(iM,&iF); *piF = (bSucces) ? iF:iD; return bSucces; }
int bS(const int iD, int *piF){ //S->AB int bSucces, iM, iF; bSucces = bA(iD,&iM) && bB(iM,&iF); *piF = (bSucces) ? iF:iD; return bSucces; }
int main(){ std::cout << "Pointer: starting unit test\n"; // int Pointer<int> a(new int(100)); Pointer<int> b(new int(200)); if(a.count() != 1) std::cout << "Pointer: unit test 1.0 failing\n"; if(b.count() != 1) std::cout << "Pointer: unit test 1.1 failing\n"; if(*a != 100) std::cout << "Pointer: unit test 1.2 failing\n"; if(*b != 200) std::cout << "Pointer: unit test 1.3 failing\n"; Pointer<int> c(a); if(a.count() != 2) std::cout << "Pointer: unit test 1.4 failing\n"; if(c.count() != 2) std::cout << "Pointer: unit test 1.5 failing\n"; if(*a != 100) std::cout << "Pointer: unit test 1.6 failing\n"; if(*c != 100) std::cout << "Pointer: unit test 1.7 failing\n"; if(a.get() != c.get()) std::cout << "Pointer: unit test 1.8 failing\n"; IPointer<int> *d = new Pointer<int>(a); if(a.count() != 3) std::cout << "Pointer: unit test 1.9 failing\n"; if(**d !=100) std::cout << "Pointer: unit test 1.10 failing\n"; delete d; if(a.count() != 2) std::cout << "Pointer: unit test 1.11 failing\n"; c = b; if(a.count() != 1) std::cout << "Pointer: unit test 1.12 failing\n"; if(b.count() != 2) std::cout << "Pointer: unit test 1.13 failing\n"; if(c.count() != 2) std::cout << "Pointer: unit test 1.14 failing\n"; if(*a != 100) std::cout << "Pointer: unit test 1.15 failing\n"; if(*b != 200) std::cout << "Pointer: unit test 1.16 failing\n"; if(*c != 200) std::cout << "Pointer: unit test 1.17 failing\n"; if(b.get() != c.get()) std::cout << "Pointer: unit test 1.18 failing\n"; a = b; if(a.count() != 3) std::cout << "Pointer: unit test 1.19 failing\n"; if(b.count() != 3) std::cout << "Pointer: unit test 1.20 failing\n"; if(c.count() != 3) std::cout << "Pointer: unit test 1.21 failing\n"; if(*a != 200) std::cout << "Pointer: unit test 1.22 failing\n"; if(*b != 200) std::cout << "Pointer: unit test 1.23 failing\n"; if(*c != 200) std::cout << "Pointer: unit test 1.24 failing\n"; if(b.get() != c.get()) std::cout << "Pointer: unit test 1.25 failing\n"; if(b.get() != a.get()) std::cout << "Pointer: unit test 1.25 failing\n"; // A Pointer<A> aA(new A(10)); Pointer<A> bA(new A(20)); if(aA.count() != 1) std::cout << "Pointer: unit test 2.0 failing\n"; if(bA.count() != 1) std::cout << "Pointer: unit test 2.1 failing\n"; if(foo(*aA) != 10) std::cout << "Pointer: unit test 2.2 failing\n"; if(foo(*bA) != 20) std::cout << "Pointer: unit test 2.3 failing\n"; if(aA->get() != 10) std::cout << "Pointer:unit test 2.4 failing\n"; if(bA->get() != 20) std::cout << "Pointer::unit test 2.5 failing\n"; Pointer<A> cA(aA); if(aA.count() != 2) std::cout << "Pointer: unit test 2.6 failing\n"; if(cA.count() != 2) std::cout << "Pointer: unit test 2.7 failing\n"; if(foo(*aA) != 10) std::cout << "Pointer: unit test 2.8 failing\n"; if(foo(*cA) != 10) std::cout << "Pointer: unit test 2.9 failing\n"; if(aA->get() != 10) std::cout << "Pointer:unit test 2.10 failing\n"; if(cA->get() != 10) std::cout << "Pointer::unit test 2.11 failing\n"; if(aA.get() != cA.get()) std::cout << "Pointer: unit test 2.12 failing\n"; IPointer<A> *dA = new Pointer<A>(aA); if(aA.count() != 3) std::cout << "Pointer: unit test 2.13 failing\n"; if(foo(**dA) != 10) std::cout << "Pointer: unit test 2.14 failing\n"; if((*dA)->get() != 10) std::cout << "Pointer: unit test 2.15 failing\n"; delete dA; if(aA.count() != 2) std::cout << "Pointer: unit test 2.16 failing\n"; cA = bA; if(aA.count() != 1) std::cout << "Pointer: unit test 2.17 failing\n"; if(bA.count() != 2) std::cout << "Pointer: unit test 2.18 failing\n"; if(cA.count() != 2) std::cout << "Pointer: unit test 2.19 failing\n"; if(foo(*aA) != 10) std::cout << "Pointer: unit test 2.20 failing\n"; if(foo(*bA) != 20) std::cout << "Pointer: unit test 2.21 failing\n"; if(foo(*cA) != 20) std::cout << "Pointer: unit test 2.22 failing\n"; if(aA->get() != 10) std::cout << "Pointer: unit test 2.23 failing\n"; if(bA->get() != 20) std::cout << "Pointer: unit test 2.24 failing\n"; if(cA->get() != 20) std::cout << "Pointer: unit test 2.25 failing\n"; if(bA.get() != cA.get()) std::cout << "Pointer: unit test 2.26 failing\n"; aA = bA; if(aA.count() != 3) std::cout << "Pointer: unit test 2.27 failing\n"; if(bA.count() != 3) std::cout << "Pointer: unit test 2.28 failing\n"; if(cA.count() != 3) std::cout << "Pointer: unit test 2.29 failing\n"; if(foo(*aA) != 20) std::cout << "Pointer: unit test 2.30 failing\n"; if(foo(*bA) != 20) std::cout << "Pointer: unit test 2.31 failing\n"; if(foo(*cA) != 20) std::cout << "Pointer: unit test 2.32 failing\n"; if(aA->get() != 20) std::cout << "Pointer: unit test 2.33 failing\n"; if(bA->get() != 20) std::cout << "Pointer: unit test 2.34 failing\n"; if(cA->get() != 20) std::cout << "Pointer: unit test 2.35 failing\n"; if(bA.get() != cA.get()) std::cout << "Pointer: unit test 2.36 failing\n"; if(bA.get() != aA.get()) std::cout << "Pointer: unit test 2.37 failing\n"; std::cout << "Pointer: unit test complete\n"; return 0; }
int main(int argc, char** argv) { if(argc != 4){ std::cout << "Error! Three arguments m, n and p are needed!" << std::endl; return 1; } int m = atoi(argv[1]); int n = atoi(argv[2]); int p = atoi(argv[3]); double elapseTime, elapseTime_single; int myrank, numprocs; MPI_Status status; MPI_Init(&argc, &argv); // 并行开始 //std::cout << "Start to computing..." << std::endl; MPI_Comm_size(MPI_COMM_WORLD, &numprocs); // 获取进程数 MPI_Comm_rank(MPI_COMM_WORLD, &myrank); // 获取本进城ID号 if(numprocs < 2){ std::cout << "Error! There must be more than two processors." << std::endl; return 1; } int bm = m / numprocs; int bn = n / numprocs; SCMatrix A(1), B(1), C(1), C_true(1); SCMatrix bA(bm,p), bB_send(bn,p), bB_recv(bn,p), bC(bm, bn), bC_send(bm, n); if(myrank == 0){ SCMatrix A1(m,p), B1(n,p), C1(m,n), C_true1(m,n); A = A1; B = B1; C = C1; C_true = C_true1; A.init_with_RV(); B.init_with_RV(); } MPI_Barrier(MPI_COMM_WORLD); //A.print(); B.print(); // start to timing clock_t start_time = clock(); //clock_t t_temp_start = clock(); MPI_Scatter(&A, bm * p, MPI_DOUBLE, &bA, bm * p, MPI_DOUBLE, 0, MPI_COMM_WORLD); MPI_Scatter(&B, bn * p, MPI_DOUBLE, &bB_recv, bn * p, MPI_DOUBLE, 0, MPI_COMM_WORLD); int sendTo = (myrank + 1) % numprocs; int recvFrom = (myrank - 1 + numprocs) % numprocs; int circle = 0; bB_send = bB_recv; do{ bC = bA * bB_recv.transpose(); int blocks_col = (myrank - circle + numprocs) % numprocs; for(int i=0; i<bm; i++){ for(int j=0; j<bn; j++){ bC_send(i, blocks_col*bn + j) = bC(i, j); } } if(myrank % 2 == 0){ bB_send = bB_recv; MPI_Ssend(&bB_send, bn*p, MPI_DOUBLE, sendTo, circle, MPI_COMM_WORLD); MPI_Recv(&bB_recv, bn*p, MPI_DOUBLE, recvFrom, circle, MPI_COMM_WORLD, &status); }else{ MPI_Recv(&bB_recv, bn*p, MPI_DOUBLE, recvFrom, circle, MPI_COMM_WORLD, &status); MPI_Ssend(&bB_send, bn*p, MPI_DOUBLE, sendTo, circle, MPI_COMM_WORLD); bB_send = bB_recv; } circle++; }while(circle < numprocs); MPI_Barrier(MPI_COMM_WORLD); MPI_Gather(&bC_send, bm * n, MPI_DOUBLE, &C, bm * n, MPI_DOUBLE, 0, MPI_COMM_WORLD); if(myrank == 0){ int remainAStartId = bm * numprocs; int remainBStartId = bn * numprocs; for(int i=remainAStartId; i<m; i++){ for(int j=0; j<n; j++){ double temp=0; for(int k=0; k<p; k++){ temp += A(i,k) * B(j,k); } C(i,j) = temp; } } for(int i=0; i<remainAStartId; i++){ for(int j=remainBStartId; j<n; j++){ double temp = 0; for(int k=0; k<p; k++){ temp += A(i,k)*B(j,k); } C(i,j) = temp; } } } // end timing clock_t end_time = clock(); elapseTime = (double)(end_time-start_time) / CLOCKS_PER_SEC; if(myrank == 0){ //std::cout << "[P_0] m = " << m << ", np = " << numprocs << ", time cost: " << elapseTime << std::endl; std::cout << "[P_0] Totally cost " << elapseTime << " seconds in parallel procedure." << std::endl; start_time = clock(); C_true = A * B.transpose(); end_time = clock(); elapseTime_single = double(end_time-start_time) / CLOCKS_PER_SEC; std::cout << "[P_0] Totally cost " << elapseTime_single << " seconds with one processor." << std::endl; bool b = (C==C_true); if(b){ std::cout << "[P_0] Congradulations! The two results are equal." << std::endl; }else{ std::cout << "[P_0] Bad news! The two results do not match." << std::endl; A.print(); B.print(); C.print(); C_true.print(); } } MPI_Finalize(); // 并行结束 return 0; }