36 #include <boost/algorithm/string.hpp>
58 UnsteadySystem(pSession),
70 int expdim =
m_graph->GetMeshDimension();
78 ASSERTL0(
false,
"Last field is defined as pressure but this is not suitable for this solver, please remove this field as it is implicitly defined");
87 ASSERTL0(
m_fields.num_elements() > 2,
"Expect to have three at least three components of velocity variables");
103 Array<OneD, MultiRegions::ExpListSharedPtr> velocity(
m_velocity.num_elements());
104 for(i =0 ; i <
m_velocity.num_elements(); ++i)
110 m_locToGloMap = Array<OneD, CoupledLocalToGlobalC0ContMapSharedPtr> (nz);
112 if(
m_session->DefinesSolverInfo(
"SingleMode"))
115 ASSERTL0(nz <=2 ,
"For single mode calculation can only have nz <= 2");
117 if(
m_session->DefinesSolverInfo(
"BetaZero"))
136 for(i = 2; i < nz; ++i)
143 else if (expdim == 3)
146 ASSERTL0(
false,
"Setup mapping aray");
150 ASSERTL0(
false,
"Exp dimension not recognised");
156 std::string vExtrapolation =
"Standard";
158 if (
m_session->DefinesSolverInfo(
"Extrapolation"))
160 vExtrapolation =
m_session->GetSolverInfo(
"Extrapolation");
195 m_mat = Array<OneD, CoupledSolverMatrices> (nz);
197 ASSERTL1(
m_npointsZ <=2,
"Only expected a maxmimum of two planes in single mode linear NS solver");
223 m_mat = Array<OneD, CoupledSolverMatrices> (nz);
228 for(n = 1; n < nz; ++n)
397 Array<OneD, unsigned int> bmap,imap;
399 Array<OneD,unsigned int> nsize_bndry (nel);
400 Array<OneD,unsigned int> nsize_bndry_p1(nel);
401 Array<OneD,unsigned int> nsize_int (nel);
402 Array<OneD,unsigned int> nsize_p (nel);
403 Array<OneD,unsigned int> nsize_p_m1 (nel);
424 for(n = 0; n < nel; ++n)
428 nsize_bndry_p1[n] = nsize_bndry[n]+nz_loc;
429 nsize_int [n] = (nvel*
m_fields[
m_velocity[0]]->GetExp(eid)->GetNcoeffs()*nz_loc - nsize_bndry[n]);
430 nsize_p[n] =
m_pressure->GetExp(eid)->GetNcoeffs()*nz_loc;
431 nsize_p_m1[n] = nsize_p[n]-nz_loc;
461 for(n = 0; n < nel; ++n)
464 nbndry = nsize_bndry[n];
466 k = nsize_bndry_p1[n];
468 Array<OneD, NekDouble> Ah_data = Ah->GetPtr();
471 Array<OneD, NekDouble> B_data = B->GetPtr();
473 Array<OneD, NekDouble> C_data = C->GetPtr();
475 Array<OneD, NekDouble> D_data = D->GetPtr();
481 locExp->GetBoundaryMap(bmap);
482 locExp->GetInteriorMap(imap);
486 locExp->DetShapeType(),
493 int nbmap = bmap.num_elements();
494 int nimap = imap.num_elements();
496 Array<OneD, NekDouble> coeffs(ncoeffs);
497 Array<OneD, NekDouble> phys (nphys);
498 int psize =
m_pressure->GetExp(eid)->GetNcoeffs();
499 int pqsize =
m_pressure->GetExp(eid)->GetTotPoints();
501 Array<OneD, NekDouble> deriv (pqsize);
502 Array<OneD, NekDouble> pcoeffs(psize);
504 if(AddAdvectionTerms ==
false)
510 CondMat = locExp->GetLocStaticCondMatrix(helmkey);
512 for(k = 0; k < nvel*nz_loc; ++k)
515 rows = SubBlock.GetRows();
516 cols = SubBlock.GetColumns();
517 for(i = 0; i < rows; ++i)
519 for(j = 0; j < cols; ++j)
521 (*Ah)(i+k*rows,j+k*cols) =
m_kinvis*SubBlock(i,j);
526 for(k = 0; k < nvel*nz_loc; ++k)
530 rows = SubBlock.GetRows();
531 cols = SubBlock.GetColumns();
532 for(i = 0; i < rows; ++i)
534 for(j = 0; j < cols; ++j)
536 (*B)(i+k*rows,j+k*cols) = SubBlock(i,j);
537 (*C)(i+k*rows,j+k*cols) =
m_kinvis*SubBlock1(j,i);
542 for(k = 0; k < nvel*nz_loc; ++k)
546 rows = SubBlock.GetRows();
547 cols = SubBlock.GetColumns();
548 for(i = 0; i < rows; ++i)
550 for(j = 0; j < cols; ++j)
552 (*D)(i+k*rows,j+k*cols) = inv_kinvis*SubBlock(i,j);
559 for(i = 0; i < bmap.num_elements(); ++i)
563 coeffs[bmap[i]] = 1.0;
567 for(j = 0; j < nvel; ++j)
569 if( (nz_loc == 2)&&(j == 2))
575 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
577 Blas::Dcopy(psize,&(pcoeffs)[0],1,
579 ((nz_loc*j+1)*bmap.num_elements()+i)*nsize_p[n],1);
582 Blas::Dcopy(psize,&(pcoeffs)[0],1,
584 ((nz_loc*j)*bmap.num_elements()+i)*nsize_p[n]+psize,1);
592 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
594 for(k = 0; k < nz_loc; ++k)
596 Blas::Dcopy(psize,&(pcoeffs)[0],1,
598 ((nz_loc*j+k)*bmap.num_elements()+i)*nsize_p[n]+ k*psize,1);
605 for(i = 0; i < imap.num_elements(); ++i)
609 coeffs[imap[i]] = 1.0;
613 for(j = 0; j < nvel; ++j)
615 if( (nz_loc == 2)&&(j == 2))
621 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
623 Blas::Dcopy(psize,&(pcoeffs)[0],1,
625 ((nz_loc*j+1)*imap.num_elements()+i)*nsize_p[n],1);
628 Blas::Dcopy(psize,&(pcoeffs)[0],1,
630 ((nz_loc*j)*imap.num_elements()+i)*nsize_p[n]+psize,1);
640 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
643 for(k = 0; k < nz_loc; ++k)
645 Blas::Dcopy(psize,&(pcoeffs)[0],1,
647 ((nz_loc*j+k)*imap.num_elements()+i)*nsize_p[n]+ k*psize,1);
661 ->GetLocMatrix(helmkey));
664 Array<OneD, const NekDouble> HelmMat_data = HelmMat.GetOwnedMatrix()->GetPtr();
665 NekDouble HelmMatScale = HelmMat.Scale();
666 int HelmMatRows = HelmMat.GetRows();
671 locExp->DetShapeType(),
674 ->GetLocMatrix(masskey);
677 Array<OneD, NekDouble> Advtmp;
678 Array<OneD, Array<OneD, NekDouble> > AdvDeriv(nvel*nvel);
680 Array<OneD, NekDouble> tmpphys =
m_fields[0]->UpdatePhys();
683 int npoints = locExp->GetTotPoints();
686 if(IsLinearNSEquation)
690 AdvDeriv[0] = Array<OneD, NekDouble>(nvel*nvel*npoints);
691 for(nv = 0; nv < nvel; ++nv)
693 for(nv1 = 0; nv1 < nvel; ++nv1)
695 if(cnt < nvel*nvel-1)
697 AdvDeriv[cnt+1] = AdvDeriv[cnt] + npoints;
714 for(i = 0; i < nbmap; ++i)
719 coeffs[bmap[i]] = 1.0;
720 locExp->BwdTrans(coeffs,phys);
722 for(k = 0; k < nvel*nz_loc; ++k)
724 for(j = 0; j < nbmap; ++j)
727 Ah_data[i+k*nbmap + (j+k*nbmap)*AhRows] +=
m_kinvis*HelmMatScale*HelmMat_data[bmap[i] + HelmMatRows*bmap[j]];
730 for(j = 0; j < nimap; ++j)
732 B_data[i+k*nbmap + (j+k*nimap)*nbndry] +=
m_kinvis*HelmMatScale*HelmMat_data[bmap[i]+HelmMatRows*imap[j]];
738 for(k = 0; k < nvel; ++k)
740 for(j = 0; j < nbmap; ++j)
742 Ah_data[i+2*k*nbmap + (j+(2*k+1)*nbmap)*AhRows] -= lambda_imag*(*MassMat)(bmap[i],bmap[j]);
745 for(j = 0; j < nbmap; ++j)
747 Ah_data[i+(2*k+1)*nbmap + (j+2*k*nbmap)*AhRows] += lambda_imag*(*MassMat)(bmap[i],bmap[j]);
750 for(j = 0; j < nimap; ++j)
752 B_data[i+2*k*nbmap + (j+(2*k+1)*nimap)*nbndry] -= lambda_imag*(*MassMat)(bmap[i],imap[j]);
755 for(j = 0; j < nimap; ++j)
757 B_data[i+(2*k+1)*nbmap + (j+2*k*nimap)*nbndry] += lambda_imag*(*MassMat)(bmap[i],imap[j]);
765 for(k = 0; k < nvel; ++k)
767 if((nz_loc == 2)&&(k == 2))
774 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
775 Blas::Dcopy(psize,&(pcoeffs)[0],1,
777 ((nz_loc*k+1)*bmap.num_elements()+i)*nsize_p[n],1);
781 Blas::Dcopy(psize,&(pcoeffs)[0],1,
783 ((nz_loc*k)*bmap.num_elements()+i)*nsize_p[n]+psize,1);
787 Advtmp = Advfield[k] + phys_offset,
788 1,deriv,1,tmpphys,1);
790 locExp->IProductWRTBase(tmpphys,coeffs);
794 for(nv = 0; nv < nvel; ++nv)
796 for(j = 0; j < nbmap; ++j)
798 Ah_data[j+2*nv*nbmap + (i+(2*nv+1)*nbmap)*AhRows] +=
802 for(j = 0; j < nimap; ++j)
804 C_data[i+(2*nv+1)*nbmap + (j+2*nv*nimap)*nbndry] +=
811 for(nv = 0; nv < nvel; ++nv)
813 for(j = 0; j < nbmap; ++j)
815 Ah_data[j+(2*nv+1)*nbmap + (i+2*nv*nbmap)*AhRows] +=
819 for(j = 0; j < nimap; ++j)
821 C_data[i+2*nv*nbmap + (j+(2*nv+1)*nimap)*nbndry] +=
832 Advtmp = Advfield[k] + phys_offset,
833 1,deriv,1,tmpphys,1);
834 locExp->IProductWRTBase(tmpphys,coeffs);
837 for(nv = 0; nv < nvel*nz_loc; ++nv)
839 for(j = 0; j < nbmap; ++j)
841 Ah_data[j+nv*nbmap + (i+nv*nbmap)*AhRows] +=
845 for(j = 0; j < nimap; ++j)
847 C_data[i+nv*nbmap + (j+nv*nimap)*nbndry] +=
853 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
854 for(j = 0; j < nz_loc; ++j)
856 Blas::Dcopy(psize,&(pcoeffs)[0],1,
858 ((nz_loc*k+j)*bmap.num_elements() + i)*nsize_p[n]+ j*psize,1);
863 if(IsLinearNSEquation)
865 for(nv = 0; nv < nvel; ++nv)
871 locExp->IProductWRTBase(tmpphys,coeffs);
873 for(
int n1 = 0; n1 < nz_loc; ++n1)
875 for(j = 0; j < nbmap; ++j)
877 Ah_data[j+(k*nz_loc+n1)*nbmap +
878 (i+(nv*nz_loc+n1)*nbmap)*AhRows] +=
882 for(j = 0; j < nimap; ++j)
884 C_data[i+(nv*nz_loc+n1)*nbmap +
885 (j+(k*nz_loc+n1)*nimap)*nbndry] +=
895 for(i = 0; i < nimap; ++i)
899 coeffs[imap[i]] = 1.0;
900 locExp->BwdTrans(coeffs,phys);
902 for(k = 0; k < nvel*nz_loc; ++k)
904 for(j = 0; j < nbmap; ++j)
906 C_data[j+k*nbmap + (i+k*nimap)*nbndry] +=
m_kinvis*HelmMatScale*HelmMat_data[imap[i]+HelmMatRows*bmap[j]];
909 for(j = 0; j < nimap; ++j)
911 D_data[i+k*nimap + (j+k*nimap)*nint] +=
m_kinvis*HelmMatScale*HelmMat_data[imap[i]+HelmMatRows*imap[j]];
917 for(k = 0; k < nvel; ++k)
919 for(j = 0; j < nbmap; ++j)
921 C_data[j+2*k*nbmap + (i+(2*k+1)*nimap)*nbndry] += lambda_imag*(*MassMat)(bmap[j],imap[i]);
924 for(j = 0; j < nbmap; ++j)
926 C_data[j+(2*k+1)*nbmap + (i+2*k*nimap)*nbndry] -= lambda_imag*(*MassMat)(bmap[j],imap[i]);
929 for(j = 0; j < nimap; ++j)
931 D_data[i+2*k*nimap + (j+(2*k+1)*nimap)*nint] -= lambda_imag*(*MassMat)(imap[i],imap[j]);
934 for(j = 0; j < nimap; ++j)
936 D_data[i+(2*k+1)*nimap + (j+2*k*nimap)*nint] += lambda_imag*(*MassMat)(imap[i],imap[j]);
942 for(k = 0; k < nvel; ++k)
944 if((nz_loc == 2)&&(k == 2))
950 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
951 Blas::Dcopy(psize,&(pcoeffs)[0],1,
953 ((nz_loc*k+1)*imap.num_elements()+i)*nsize_p[n],1);
956 Blas::Dcopy(psize,&(pcoeffs)[0],1,
958 ((nz_loc*k)*imap.num_elements()+i)*nsize_p[n]+psize,1);
962 Vmath::Vmul(npoints, Advtmp = Advfield[k] + phys_offset,1,deriv,1,tmpphys,1);
963 locExp->IProductWRTBase(tmpphys,coeffs);
966 for(nv = 0; nv < nvel; ++nv)
968 for(j = 0; j < nbmap; ++j)
970 B_data[j+2*nv*nbmap + (i+(2*nv+1)*nimap)*nbndry] +=
974 for(j = 0; j < nimap; ++j)
976 D_data[j+2*nv*nimap + (i+(2*nv+1)*nimap)*nint] +=
982 for(nv = 0; nv < nvel; ++nv)
984 for(j = 0; j < nbmap; ++j)
986 B_data[j+(2*nv+1)*nbmap + (i+2*nv*nimap)*nbndry] +=
990 for(j = 0; j < nimap; ++j)
992 D_data[j+(2*nv+1)*nimap + (i+2*nv*nimap)*nint] +=
1006 Advtmp = Advfield[k] + phys_offset,
1007 1,deriv,1,tmpphys,1);
1008 locExp->IProductWRTBase(tmpphys,coeffs);
1011 for(nv = 0; nv < nvel*nz_loc; ++nv)
1013 for(j = 0; j < nbmap; ++j)
1015 B_data[j+nv*nbmap + (i+nv*nimap)*nbndry] +=
1019 for(j = 0; j < nimap; ++j)
1021 D_data[j+nv*nimap + (i+nv*nimap)*nint] +=
1026 m_pressure->GetExp(eid)->IProductWRTBase(deriv,pcoeffs);
1027 for(j = 0; j < nz_loc; ++j)
1029 Blas::Dcopy(psize,&(pcoeffs)[0],1,
1031 ((nz_loc*k+j)*imap.num_elements() + i)*nsize_p[n]+j*psize,1);
1036 if(IsLinearNSEquation)
1039 for(nv = 0; nv < nvel; ++nv)
1043 AdvDeriv[k*nvel+nv],
1045 locExp->IProductWRTBase(tmpphys,coeffs);
1047 for(n1 = 0; n1 < nz_loc; ++n1)
1049 for(j = 0; j < nbmap; ++j)
1051 B_data[j+(k*nz_loc+n1)*nbmap +
1052 (i+(nv*nz_loc+n1)*nimap)*nbndry] +=
1056 for(j = 0; j < nimap; ++j)
1058 D_data[j+(k*nz_loc+n1)*nimap +
1059 (i+(nv*nz_loc+n1)*nimap)*nint] +=
1076 Blas::Dgemm(
'N',
'T', B->GetRows(), C->GetRows(),
1077 B->GetColumns(), -1.0, B->GetRawPtr(),
1078 B->GetRows(), C->GetRawPtr(),
1080 Ah->GetRawPtr(), Ah->GetRows());
1093 DNekMat DintCinvDTint, BCinvDTint_m_DTbnd, DintCinvBTtilde_m_Dbnd;
1099 DintCinvDTint = (*Dint)*(*Cinv)*
Transpose(*Dint);
1103 DintCinvBTtilde_m_Dbnd = (*Dint)*(*Cinv)*
Transpose(*Btilde) - (*Dbnd);
1109 Array<OneD, NekDouble> Dh_data = Dh->GetPtr();
1113 for(n1 = 0; n1 < nz_loc; ++n1)
1115 for(i = 0; i < psize-1; ++i)
1117 for(n2 = 0; n2 < nz_loc; ++n2)
1119 for(j = 0; j < psize-1; ++j)
1123 Dh_data[(i+n1*(psize-1)) + (j+n2*(psize-1))*Dh->GetRows()] =
1124 -DintCinvDTint(i+1+n1*psize,j+1+n2*psize);
1130 for(n1 = 0; n1 < nz_loc; ++n1)
1132 for(i = 0; i < nsize_bndry_p1[n]-nz_loc; ++i)
1134 (*Ah)(i,nsize_bndry_p1[n]-nz_loc+n1) = BCinvDTint_m_DTbnd(i,n1*psize);
1135 (*Ah)(nsize_bndry_p1[n]-nz_loc+n1,i) = DintCinvBTtilde_m_Dbnd(n1*psize,i);
1139 for(n1 = 0; n1 < nz_loc; ++n1)
1141 for(n2 = 0; n2 < nz_loc; ++n2)
1143 (*Ah)(nsize_bndry_p1[n]-nz_loc+n1,nsize_bndry_p1[n]-nz_loc+n2) =
1144 -DintCinvDTint(n1*psize,n2*psize);
1148 for(n1 = 0; n1 < nz_loc; ++n1)
1150 for(j = 0; j < psize-1; ++j)
1152 for(i = 0; i < nsize_bndry_p1[n]-nz_loc; ++i)
1154 (*Bh)(i,j+n1*(psize-1)) = BCinvDTint_m_DTbnd(i,j+1+n1*psize);
1155 (*Ch)(j+n1*(psize-1),i) = DintCinvBTtilde_m_Dbnd(j+1+n1*psize,i);
1160 for(n1 = 0; n1 < nz_loc; ++n1)
1162 for(n2 = 0; n2 < nz_loc; ++n2)
1164 for(j = 0; j < psize-1; ++j)
1166 (*Bh)(nsize_bndry_p1[n]-nz_loc+n1,j+n2*(psize-1)) = -DintCinvDTint(n1*psize,j+1+n2*psize);
1167 (*Ch)(j+n2*(psize-1),nsize_bndry_p1[n]-nz_loc+n1) = -DintCinvDTint(j+1+n2*psize,n1*psize);
1174 (*Bh) = (*Bh)*(*Dh);
1176 Blas::Dgemm(
'N',
'N', Bh->GetRows(), Ch->GetColumns(), Bh->GetColumns(), -1.0,
1177 Bh->GetRawPtr(), Bh->GetRows(), Ch->GetRawPtr(), Ch->GetRows(),
1178 1.0, Ah->GetRawPtr(), Ah->GetRows());
1188 cout <<
"Matrix Setup Costs: " << timer.
TimePerTest(1) << endl;
1200 cout <<
"Multilevel condensation: " << timer.
TimePerTest(1) << endl;
1247 Array<OneD, Array<OneD, NekDouble> > AdvField(
m_velocity.num_elements());
1248 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1254 "Advection Velocity section must be defined in "
1257 std::vector<std::string> fieldStr;
1258 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1282 "Restart section must be defined in session file.");
1284 Array<OneD, Array<OneD, NekDouble> > Restart(
m_velocity.num_elements());
1285 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1289 std::vector<std::string> fieldStr;
1290 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1296 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1300 cout <<
"Saving the RESTART file for m_kinvis = "<<
m_kinvis <<
" (<=> Re = " << 1/
m_kinvis <<
")" <<endl;
1319 cout <<
"Saving the Stokes Flow for m_kinvis = "<<
m_kinvis <<
" (<=> Re = " << 1/
m_kinvis <<
")" <<endl;
1327 Array<OneD, Array<OneD, NekDouble> > AdvField(
m_velocity.num_elements());
1328 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1334 "Advection Velocity section must be defined in "
1337 std::vector<std::string> fieldStr;
1338 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1349 ASSERTL0(
false,
"Unknown or undefined equation type for CoupledLinearNS");
1354 Array<
OneD, Array<OneD, NekDouble> > &outarray,
1360 std::vector<SolverUtils::ForcingSharedPtr>::const_iterator x;
1363 (*x)->Apply(
m_fields, outarray, outarray, time);
1368 Array<
OneD, Array<OneD, NekDouble> > &outarray,
1376 Array <OneD, Array<OneD, NekDouble> > forcing(
m_velocity.num_elements());
1378 if(fabs(lambda_store - lambda) > 1e-10)
1380 cout <<
"Setting up Stokes matrix problem [.";
1383 cout <<
"]" << endl;
1384 lambda_store = lambda;
1390 for(i = 0; i <
m_velocity.num_elements(); ++i)
1399 for(i = 0; i <
m_velocity.num_elements(); ++i)
1408 int nfields =
m_fields.num_elements();
1409 for (
int k=0 ; k < nfields; ++k)
1420 int nfields =
m_fields.num_elements();
1421 for (
int k=0 ; k < nfields; ++k)
1449 Generaltimer.
Start();
1457 cout<<
"We execute INITIALLY SolveSteadyNavierStokes for m_kinvis = "<<
m_kinvis<<
" (<=> Re = "<<1/
m_kinvis<<
")"<<endl;
1464 cout<<
"We execute SolveSteadyNavierStokes for m_kinvis = "<<
m_kinvis<<
" (<=> Re = "<<1/
m_kinvis<<
")"<<endl;
1474 cout<<
"We execute SolveSteadyNavierStokes for m_kinvis = "<<
m_kinvis<<
" (<=> Re = "<<1/
m_kinvis<<
")"<<endl;
1482 Generaltimer.
Stop();
1483 cout<<
"\nThe total calculation time is : " << Generaltimer.
TimePerTest(1)/60 <<
" minute(s). \n\n";
1489 ASSERTL0(
false,
"Unknown or undefined equation type for CoupledLinearNS");
1497 const unsigned int ncmpt =
m_velocity.num_elements();
1498 Array<OneD, Array<OneD, NekDouble> > forcing_phys(ncmpt);
1499 Array<OneD, Array<OneD, NekDouble> > forcing (ncmpt);
1501 for(
int i = 0; i < ncmpt; ++i)
1503 forcing_phys[i] = Array<OneD, NekDouble> (
m_fields[
m_velocity[0]]->GetNpoints(), 0.0);
1507 std::vector<SolverUtils::ForcingSharedPtr>::const_iterator x;
1511 (*x)->Apply(
m_fields, forcing_phys, forcing_phys, time);
1513 for (
unsigned int i = 0; i < ncmpt; ++i)
1515 m_fields[i]->IProductWRTBase(forcing_phys[i], forcing[i]);
1520 m_fields[i]->HomogeneousFwdTrans(forcing[i], forcing[i]);
1533 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1536 m_ForcingTerm_Coeffs[i] = Array<OneD, NekDouble> (
m_fields[
m_velocity[i]]->GetNcoeffs(),0.0);
1539 if(
m_session->DefinesFunction(
"ForcingTerm"))
1541 std::vector<std::string> fieldStr;
1542 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1547 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1554 cout <<
"'ForcingTerm' section has not been defined in the input file => forcing=0" << endl;
1561 Newtontimer.
Start();
1563 Array<OneD, Array<OneD, NekDouble> > RHS_Coeffs(
m_velocity.num_elements());
1564 Array<OneD, Array<OneD, NekDouble> > RHS_Phys(
m_velocity.num_elements());
1565 Array<OneD, Array<OneD, NekDouble> > delta_velocity_Phys(
m_velocity.num_elements());
1566 Array<OneD, Array<OneD, NekDouble> >Velocity_Phys(
m_velocity.num_elements());
1567 Array<OneD, NekDouble > L2_norm(
m_velocity.num_elements(), 1.0);
1568 Array<OneD, NekDouble > Inf_norm(
m_velocity.num_elements(), 1.0);
1570 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1572 delta_velocity_Phys[i] = Array<OneD, NekDouble> (
m_fields[
m_velocity[i]]->GetTotPoints(),1.0);
1573 Velocity_Phys[i] = Array<OneD, NekDouble> (
m_fields[
m_velocity[i]]->GetTotPoints(),0.0);
1578 L2Norm(delta_velocity_Phys, L2_norm);
1581 while(max(L2_norm[0], L2_norm[1]) >
m_tol)
1586 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1592 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1614 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1620 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1622 Vmath::Vadd(Velocity_Phys[i].num_elements(),Velocity_Phys[i], 1, delta_velocity_Phys[i], 1,
1623 Velocity_Phys[i], 1);
1627 L2Norm(delta_velocity_Phys, L2_norm);
1629 if(max(Inf_norm[0], Inf_norm[1]) > 100)
1631 cout<<
"\nThe Newton method has failed at m_kinvis = "<<
m_kinvis<<
" (<=> Re = " << 1/
m_kinvis <<
")"<< endl;
1632 ASSERTL0(0,
"The Newton method has failed... \n");
1642 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1649 cout<<
"We have done "<<
m_counter-1 <<
" iteration(s) in " << Newtontimer.
TimePerTest(1)/60 <<
" minute(s). \n\n";
1655 Array<OneD, Array<OneD, NekDouble> > u_N(
m_velocity.num_elements());
1656 Array<OneD, Array<OneD, NekDouble> > tmp_RHS(
m_velocity.num_elements());
1657 Array<OneD, Array<OneD, NekDouble> > RHS(
m_velocity.num_elements());
1658 Array<OneD, Array<OneD, NekDouble> > u_star(
m_velocity.num_elements());
1660 cout <<
"We apply the continuation method: " <<endl;
1662 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1679 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1686 Vmath::Vadd(u_star[i].num_elements(), u_star[i], 1, u_N[i], 1, u_star[i], 1);
1696 Array<OneD, NekDouble> &outarray)
1698 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1701 for(
int j = 0; j < inarray[i].num_elements(); ++j)
1703 if(inarray[i][j] > outarray[i])
1705 outarray[i] = inarray[i][j];
1708 cout <<
"InfNorm["<<i<<
"] = "<< outarray[i] <<endl;
1713 Array<OneD, NekDouble> &outarray)
1715 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1718 for(
int j = 0; j < inarray[i].num_elements(); ++j)
1720 outarray[i] += inarray[i][j]*inarray[i][j];
1722 outarray[i]=sqrt(outarray[i]);
1723 cout <<
"L2Norm["<<i<<
"] = "<< outarray[i] <<endl;
1729 Array<
OneD, Array<OneD, NekDouble> > &outarray)
1731 Array<OneD, Array<OneD, NekDouble> > Eval_Adv(
m_velocity.num_elements());
1732 Array<OneD, Array<OneD, NekDouble> > tmp_DerVel(
m_velocity.num_elements());
1733 Array<OneD, Array<OneD, NekDouble> > AdvTerm(
m_velocity.num_elements());
1734 Array<OneD, Array<OneD, NekDouble> > ViscTerm(
m_velocity.num_elements());
1735 Array<OneD, Array<OneD, NekDouble> > Forc(
m_velocity.num_elements());
1737 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1740 tmp_DerVel[i] = Array<OneD, NekDouble> (
m_fields[
m_velocity[i]]->GetTotPoints(),0.0);
1754 for(
int i = 0; i <
m_velocity.num_elements(); ++i)
1760 Vmath::Vsub(outarray[i].num_elements(), outarray[i], 1, AdvTerm[i], 1, outarray[i], 1);
1761 Vmath::Vsub(outarray[i].num_elements(), outarray[i], 1, ViscTerm[i], 1, outarray[i], 1);
1763 Vmath::Vadd(outarray[i].num_elements(), outarray[i], 1, Forc[i], 1, outarray[i], 1);
1776 SpatialDomains::ExpansionMap::const_iterator expMapIter;
1779 for (expMapIter = VelExp.begin(); expMapIter != VelExp.end(); ++expMapIter)
1783 for(i = 0; i < expMapIter->second->m_basisKeyVector.size(); ++i)
1787 ASSERTL0(nummodes > 3,
"Velocity polynomial space not sufficiently high (>= 4)");
1790 BasisVec.push_back(newB);
1796 (*returnval)[expMapIter->first] = expansionElementShPtr;
1800 m_graph->SetExpansions(
"p",returnval);
1872 Array<OneD, MultiRegions::ExpListSharedPtr> vel_fields(
m_velocity.num_elements());
1873 Array<OneD, Array<OneD, NekDouble> > force(
m_velocity.num_elements());
1881 for(i = 0; i <
m_velocity.num_elements(); ++i)
1885 force[i] = forcing[i] + 2*n*ncoeffsplane;
1890 for(i = 0; i <
m_velocity.num_elements(); ++i)
1898 for(i = 0; i <
m_velocity.num_elements(); ++i)
1902 force[i] = forcing[i];
1910 int i,j,k,n,eid,cnt,cnt1;
1911 int nbnd,nint,offset;
1913 int nel = fields[0]->GetNumElmts();
1914 Array<OneD, unsigned int> bmap, imap;
1916 Array<OneD, NekDouble > f_bnd(
m_mat[mode].m_BCinv->GetRows());
1918 Array<OneD, NekDouble > f_int(
m_mat[mode].m_BCinv->GetColumns());
1922 int nplanecoeffs = fields[
m_velocity[0]]->GetNcoeffs();
1940 for(i = 0; i < fields.num_elements(); ++i)
1944 Vmath::Zero(2*pressure->GetNcoeffs(),pressure->UpdateCoeffs(),1);
1951 for(i = 0; i < nel; ++i)
1953 eid = fields[
m_velocity[0]]->GetOffset_Elmt_Id(i);
1954 fields[
m_velocity[0]]->GetExp(eid)->GetBoundaryMap(bmap);
1955 fields[
m_velocity[0]]->GetExp(eid)->GetInteriorMap(imap);
1956 nbnd = bmap.num_elements();
1957 nint = imap.num_elements();
1958 offset = fields[
m_velocity[0]]->GetCoeff_Offset(eid);
1960 for(j = 0; j < nvel; ++j)
1962 for(n = 0; n < nz_loc; ++n)
1964 for(k = 0; k < nbnd; ++k)
1966 f_bnd[cnt+k] = forcing[j][n*nplanecoeffs +
1969 for(k = 0; k < nint; ++k)
1971 f_int[cnt1+k] = forcing[j][n*nplanecoeffs +
1980 Array<OneD, NekDouble > f_p(
m_mat[mode].m_D_int->GetRows());
1985 F_bnd = F_bnd - (*
m_mat[mode].m_BCinv)*F_int;
1986 F_p_tmp = (*
m_mat[mode].m_Cinv)*F_int;
1987 F_p = (*
m_mat[mode].m_D_int) * F_p_tmp;
1990 Array<OneD, NekDouble > bnd (
m_locToGloMap[mode]->GetNumGlobalCoeffs(),0.0);
1991 Array<OneD, NekDouble > fh_bnd(
m_locToGloMap[mode]->GetNumGlobalCoeffs(),0.0);
1993 const Array<OneD,const int>& loctoglomap
1995 const Array<OneD,const NekDouble>& loctoglosign
1999 for(i = 0; i < nel; ++i)
2001 eid = fields[0]->GetOffset_Elmt_Id(i);
2002 nbnd = nz_loc*fields[0]->GetExp(eid)->NumBndryCoeffs();
2004 for(j = 0; j < nvel; ++j)
2006 for(k = 0; k < nbnd; ++k)
2008 fh_bnd[loctoglomap[offset+j*nbnd+k]] +=
2009 loctoglosign[offset+j*nbnd+k]*f_bnd[cnt+k];
2014 nint = pressure->GetExp(eid)->GetNcoeffs();
2015 offset += nvel*nbnd + nint*nz_loc;
2019 for(i = 0; i < nel; ++i)
2021 eid = fields[0]->GetOffset_Elmt_Id(i);
2022 nbnd = nz_loc*fields[0]->GetExp(eid)->NumBndryCoeffs();
2023 nint = pressure->GetExp(eid)->GetNcoeffs();
2025 for(n = 0; n < nz_loc; ++n)
2027 for(j = 0; j < nint; ++j)
2029 fh_bnd[loctoglomap[offset + nvel*nbnd + n*nint+j]] = f_p[cnt1+j];
2033 offset += nvel*nbnd + nz_loc*nint;
2037 const Array<OneD,const int>& bndmap
2044 for(k = 0; k < nvel; ++k)
2046 const Array<OneD, SpatialDomains::BoundaryConditionShPtr> bndConds = fields[k]->GetBndConditions();
2047 Array<OneD, const MultiRegions::ExpListSharedPtr> bndCondExp;
2050 bndCondExp =
m_fields[k]->GetPlane(2*mode)->GetBndCondExpansions();
2054 bndCondExp =
m_fields[k]->GetBndCondExpansions();
2057 for(i = 0; i < bndCondExp.num_elements(); ++i)
2059 const Array<OneD, const NekDouble > bndCondCoeffs = bndCondExp[i]->GetCoeffs();
2061 for(n = 0; n < nz_loc; ++n)
2063 if(bndConds[i]->GetBoundaryConditionType()
2066 for(j = 0; j < (bndCondExp[i])->
GetNcoeffs(); j++)
2072 bnd[bndmap[bndcnt++]] = 0;
2076 bnd[bndmap[bndcnt++]] = bndCondCoeffs[cnt++];
2082 for(j = 0; j < (bndCondExp[i])->
GetNcoeffs(); j++)
2084 fh_bnd[bndmap[bndcnt++]]
2085 += bndCondCoeffs[cnt++];
2096 int totpcoeffs = pressure->GetNcoeffs();
2097 Array<OneD, NekDouble> p_coeffs = pressure->UpdateCoeffs();
2098 for(i = 0; i < nel; ++i)
2100 eid = fields[0]->GetOffset_Elmt_Id(i);
2101 nbnd = nz_loc*fields[0]->GetExp(eid)->NumBndryCoeffs();
2102 nint = pressure->GetExp(eid)->GetNcoeffs();
2104 for(j = 0; j < nvel; ++j)
2106 for(k = 0; k < nbnd; ++k)
2108 f_bnd[cnt+k] = loctoglosign[offset+j*nbnd+k]*bnd[loctoglomap[offset + j*nbnd + k]];
2112 offset += nvel*nbnd + nint*nz_loc;
2115 pressure->SetPhysState(
false);
2117 offset = cnt = cnt1 = 0;
2118 for(i = 0; i < nel; ++i)
2120 eid = fields[0]->GetOffset_Elmt_Id(i);
2121 nint = pressure->GetExp(eid)->GetNcoeffs();
2122 nbnd = fields[0]->GetExp(eid)->NumBndryCoeffs();
2123 cnt1 = pressure->GetCoeff_Offset(eid);
2125 for(n = 0; n < nz_loc; ++n)
2127 for(j = 0; j < nint; ++j)
2129 p_coeffs[n*totpcoeffs + cnt1+j] =
2130 f_p[cnt+j] = bnd[loctoglomap[offset +
2131 (nvel*nz_loc)*nbnd +
2136 offset += (nvel*nbnd + nint)*nz_loc;
2143 F_int = (*
m_mat[mode].m_Cinv)*F_int;
2147 for(i = 0; i < nel; ++i)
2149 eid = fields[
m_velocity[0]]->GetOffset_Elmt_Id(i);
2150 fields[0]->GetExp(eid)->GetBoundaryMap(bmap);
2151 fields[0]->GetExp(eid)->GetInteriorMap(imap);
2152 nbnd = bmap.num_elements();
2153 nint = imap.num_elements();
2154 offset = fields[0]->GetCoeff_Offset(eid);
2156 for(j = 0; j < nvel; ++j)
2158 for(n = 0; n < nz_loc; ++n)
2160 for(k = 0; k < nbnd; ++k)
2162 fields[j]->SetCoeff(n*nplanecoeffs +
2167 for(k = 0; k < nint; ++k)
2169 fields[j]->SetCoeff(n*nplanecoeffs +
2179 for(j = 0; j < nvel; ++j)
2181 fields[j]->SetPhysState(
false);
2187 std::vector<Array<OneD, NekDouble> > fieldcoeffs(
m_fields.num_elements()+1);
2188 std::vector<std::string> variables(
m_fields.num_elements()+1);
2191 for(i = 0; i <
m_fields.num_elements(); ++i)
2193 fieldcoeffs[i] =
m_fields[i]->UpdateCoeffs();
2197 fieldcoeffs[i] = Array<OneD, NekDouble>(
m_fields[0]->GetNcoeffs());
2204 m_fields[0]->GetPlane(0)->FwdTrans_IterPerExp(
m_pressure->GetPlane(0)->GetPhys(),fieldcoeffs[i]);
2205 m_fields[0]->GetPlane(1)->FwdTrans_IterPerExp(
m_pressure->GetPlane(1)->GetPhys(),tmpfieldcoeffs);
2206 for(
int e=0; e<
m_fields[0]->GetNcoeffs()/2; e++)
2208 fieldcoeffs[i][e+
m_fields[0]->GetNcoeffs()/2] = tmpfieldcoeffs[e];
2225 return m_session->GetVariables().size();