示例#1
0
std::vector<std::vector<int>> primeFactor(int n, const std::set<int>& primes)
{
	std::vector<std::vector<int>> facs(n+1);
	for (auto p:primes)
	{
		for(int i = 2*p; i <= n ; i += p)
			facs[i].emplace_back(p);
	}

	std::function<void(int,int,int,const std::vector<int>&,std::vector<int>&)> tranverse = [&tranverse](int l,int i,int m,const std::vector<int>& f, std::vector<int>& lf)
	{
		if(l == 0)
		{
			lf.emplace_back(m);
			return ;
		}
		else
		{
			for(int j = i+1 ; j <= f.size() - l ; ++ j)
				tranverse(l-1,j,m*f[j],f,lf);
		}
	};

	long whole_count = 0;
	for (int i = 2 ; i <= n ; ++ i)
	{
		int count = i-1;
		int t = -1;
		for(int l = 1 ; l <= facs[i].size() ; ++ l)
		{
			std::vector<int> lf;
			tranverse(l,-1,1,facs[i],lf);
			for(auto f:lf)
				count += t*(i/f-1);
			t = -t;
		}
		whole_count+=count;
	}
	std::cout<<whole_count<<std::endl;
	return facs;
}
示例#2
0
void StrandBlockSolver::gradQa(const int& mglevel)
{
  if (mglevel == 0 && gradient != 0 && gradQaFlag == 0){

    // compute nodal values
    nodalQa(mglevel);


    // initialize gradients
    for (int n=0; n<nFaces+nBedges; n++)
      for (int j=0; j<nPstr+2; j++)
	for (int k=0; k<ndim; k++)
	  for (int m=0; m<nqa; m++) qax(m,k,j,n) = 0.;


    // loop through unstructured edges
    int c1,c2,n1,n2,jm,jp,k;
    double Ax,Ay,sqa;
    for (int n=0; n<nEdges; n++){
      c1             = edge(0,n);
      c2             = edge(1,n);
      n1             = edgn(n);
    for (int j=1; j<nPstr+1; j++){
      jm             = j-1;
      Ax             = facs(0,j,n);
      Ay             = facs(1,j,n);
    for (int kk=0; kk<nqaGradQa; kk++){
      k              = iqagrad(kk);
      sqa            = qap(k,jm,n1)+qap(k,j,n1);
      qax(k,0,j,c1) += Ax*sqa;
      qax(k,1,j,c1) += Ay*sqa;
      qax(k,0,j,c2) -= Ax*sqa;
      qax(k,1,j,c2) -= Ay*sqa;
    }}}


    // loop through structured edges
    for (int n=0; n<nFaces-nGfaces; n++){
      n1             = face(0,n);
      n2             = face(1,n);
    for (int j=0; j<nPstr+1; j++){
      jp             = j+1;
      Ax             = facu(0,j,n);
      Ay             = facu(1,j,n);
    for (int kk=0; kk<nqaGradQa; kk++){
      k              = iqagrad(kk);
      sqa            = qap(k,j,n1)+qap(k,j,n2);
      qax(k,0,j ,n) += Ax*sqa;
      qax(k,1,j ,n) += Ay*sqa;
      qax(k,0,jp,n) -= Ax*sqa;
      qax(k,1,jp,n) -= Ay*sqa;
    }}}


    // divide by twice the volume for the interior cells
    for (int n=0; n<nFaces-nGfaces; n++)
      for (int j=1; j<nPstr+1; j++)
	for (int m=0; m<ndim; m++)
	  for (int kk=0; kk<nqaGradQa; kk++){
	    k             = iqagrad(kk);
	    qax(k,m,j,n) /= (2.*v(j,n));
	  }


    // surface, end, and boundary gradients
    double dx1,dy1,dx2,dy2,ds,l11,l12,l21,l22,sqa1,sqa2,eps=1.e-14;
    int j=0;
    jp = 1;
    for (int n=0; n<nFaces-nGfaces; n++){
      n1           = face(0,n);
      n2           = face(1,n);
      dx1          = x (0,j ,n2)-x (0,j,n1);
      dy1          = x (1,j ,n2)-x (1,j,n1);
      dx2          = xc(0,jp,n )-xc(0,j,n );
      dy2          = xc(1,jp,n )-xc(1,j,n );
      ds           = dx1*dy2-dx2*dy1;
      if (fabs(ds) < eps) ds = 0.; // on sharp corners qax = 0.
      else ds = 1./ds;
      l11          = ds*dy2;
      l12          =-ds*dy1;
      l21          =-ds*dx2;
      l22          = ds*dx1;
    for (int kk=0; kk<nqaGradQa; kk++){
      k            = iqagrad(kk);
      sqa1         = qap(k,j ,n2)-qap(k,j,n1);
      sqa2         = qa (k,jp,n )-qa (k,j,n );
      qax(k,0,j,n) = l11*sqa1+l12*sqa2;
      qax(k,1,j,n) = l21*sqa1+l22*sqa2;
    }}

    j  = nPstr+1;
    jm = nPstr;
    for (int n=0; n<nFaces-nGfaces; n++){
      n1           = face(0,n);
      n2           = face(1,n);
      dx1          = x (0,j ,n2)-x (0,j,n1);
      dy1          = x (1,j ,n2)-x (1,j,n1);
      dx2          = xc(0,jm,n )-xc(0,j,n );
      dy2          = xc(1,jm,n )-xc(1,j,n );
      ds           = dx1*dy2-dx2*dy1;
      if (fabs(ds) < eps) ds = 0.;
      else ds = 1./ds;
      l11          = ds*dy2;
      l12          =-ds*dy1;
      l21          =-ds*dx2;
      l22          = ds*dx1;
    for (int kk=0; kk<nqaGradQa; kk++){
      k            = iqagrad(kk);
      sqa1         = qap(k,j ,n2)-qap(k,j,n1);
      sqa2         = qa (k,jm,n )-qa (k,j,n );
      qax(k,0,j,n) = l11*sqa1+l12*sqa2;
      qax(k,1,j,n) = l21*sqa1+l22*sqa2;
    }}

    for (int n=nEdges-nBedges; n<nEdges; n++){
      c1            = edge(0,n);
      c2            = edge(1,n);
      n1            = edgn(  n);
    for (int j=1; j<nPstr+1; j++){
      jm            = j-1;
      dx1           = x (0,j,n1)-x (0,jm,n1);
      dy1           = x (1,j,n1)-x (1,jm,n1);
      dx2           = xc(0,j,c1)-xc(0,j ,c2);
      dy2           = xc(1,j,c1)-xc(1,j ,c2);
      ds  = dx1*dy2-dx2*dy1;
      if (fabs(ds) < eps) ds = 0.;
      else ds  = 1./ds;
      l11           = ds*dy2;
      l12           =-ds*dy1;
      l21           =-ds*dx2;
      l22           = ds*dx1;
    for (int kk=0; kk<nqaGradQa; kk++){
      k             = iqagrad(kk);
      sqa1          = qap(k,j,n1)-qap(k,jm,n1);
      sqa2          = qa (k,j,c1)-qa (k,j ,c2);
      qax(k,0,j,c2) = l11*sqa1+l12*sqa2;
      qax(k,1,j,c2) = l21*sqa1+l22*sqa2;
    }}}
    gradQaFlag = 1;
  }
}
示例#3
0
void StrandBlockSolver::rhsViscousFine()
{
  int c1,c2,n1,n2,fc,jm,jp,npts=1;
  double dx1,dy1,dx2,dy2,ds,dq1,dq2,eps=1.e-14,
    qxe[nq],qye[nq],qaxe[nqa],qaye[nqa],qe[nq],qae[nqa],fv[nq];


  // unstructured faces
  for (int n=0; n<nEdges; n++){
    c1             = edge(0,n);
    c2             = edge(1,n);
    n1             = edgn(n);
    fc             = fClip(c1);
    if (fClip(c2) > fc) fc = fClip(c2);
    for (int j=1; j<fc+1; j++){
      jm           = j-1;
      dx1          = x (0,j,n1)-x (0,jm,n1);
      dy1          = x (1,j,n1)-x (1,jm,n1);
      dx2          = xc(0,j,c2)-xc(0,j ,c1);
      dy2          = xc(1,j,c2)-xc(1,j ,c1);
      ds           = 1./(dx1*dy2-dx2*dy1);
      for (int k=0; k<nq; k++){
	dq1        = qp(k,j,n1)-qp(k,jm,n1);
	dq2        = q (k,j,c2)-q (k,j ,c1);
	qxe[k]     = ds*( dy2*dq1-dy1*dq2);
	qye[k]     = ds*(-dx2*dq1+dx1*dq2);
	qe[k]      = .5*(qp (k,j,n1)+qp (k,jm,n1));
      }
      for (int k=0; k<nqa; k++){
	dq1        = qap(k,j,n1)-qap(k,jm,n1);
	dq2        = qa (k,j,c2)-qa (k,j ,c1);
	qaxe[k]    = ds*( dy2*dq1-dy1*dq2);
	qaye[k]    = ds*(-dx2*dq1+dx1*dq2);
	qae[k]     = .5*(qap(k,j,n1)+qap(k,jm,n1));
      }
      sys->rhsVisFlux(npts,&facs(0,j,n),&qe[0],&qae[0],&qxe[0],&qye[0],
		      &qaxe[0],&qaye[0],&fv[0]);
      for (int k=0; k<nq; k++){
	r(k,j,c1) -= fv[k];
	r(k,j,c2) += fv[k];
      }}}


  // structured faces
  for (int n=0; n<nFaces-nGfaces; n++){
    n1             = face(0,n);
    n2             = face(1,n);
    for (int j=0; j<fClip(n)+1; j++){
      jp           = j+1;
      dx1          = x (0,j ,n2)-x (0,j,n1);
      dy1          = x (1,j ,n2)-x (1,j,n1);
      dx2          = xc(0,jp,n )-xc(0,j,n );
      dy2          = xc(1,jp,n )-xc(1,j,n );
      ds           = dx1*dy2-dx2*dy1;
      if (fabs(ds) < eps) for (int k=0; k<nq; k++) fv[k] = 0.;
      else{
	ds         = 1./ds;
	for (int k=0; k<nq; k++){
	  dq1      = qp(k,j ,n2)-qp(k,j,n1);
	  dq2      = q (k,jp,n )-q (k,j,n );
	  qxe[k]   = ds*( dy2*dq1-dy1*dq2);
	  qye[k]   = ds*(-dx2*dq1+dx1*dq2);
	  qe[k]    = .5*(qp (k,j,n1)+qp (k,j,n2));
	}
	for (int k=0; k<nqa; k++){
	  dq1      = qap(k,j ,n2)-qap(k,j,n1);
	  dq2      = qa (k,jp,n )-qa (k,j,n );
	  qaxe[k]  = ds*( dy2*dq1-dy1*dq2);
	  qaye[k]  = ds*(-dx2*dq1+dx1*dq2);
	  qae[k]   = .5*(qap(k,j,n1)+qap(k,j,n2));
	}
	sys->rhsVisFlux(npts,&facu(0,j,n),&qe[0],&qae[0],&qxe[0],&qye[0],
			&qaxe[0],&qaye[0],&fv[0]);
      }
      for (int k=0; k<nq; k++){
	r(k,j ,n) -= fv[k];
	r(k,jp,n) += fv[k];
      }}}
}
示例#4
0
void StrandBlockSolver::lhsTime(const int& step,
				const int& pseudoStep)
{
  // compute inviscid and viscous spectral radius
  specRadi();
  specRadv();


  // add physical time derivative to LHS
  if (step > 0){
    int jj=1,m;
    double tj[nq*nq],a=1.5/dtUnsteady,b;
    for (int n=0; n<nFaces-nGfaces; n++)
    for (int j=1; j<fClip(n)+1; j++){
      b = a*v(j,n);
      sys->lhsConsVarJacobian(jj,&q(0,j,n),&qa(0,j,n),&tj[0]);
      for (int k=0; k<nq; k++){
	m = k*nq;
      for (int l=0; l<nq; l++) dd(l,k,j,n) = tj[m+l]*b;
      }}}


  // compute the pseudo time step using sum of face areas around a cell
  // in place of volume, and add to LHS
  int j=nPstr+2,k=nFaces+nBedges,c1,c2,m;
  double Ax,Ay,A;
  Array2D<double> ll(j,k);
  for (int n=0; n<nFaces+nBedges; n++)
  for (int j=0; j<nPstr+2; j++) ll(j,n) = 0.;

  for (int n=0; n<nEdges; n++){
    c1       = edge(0,n);
    c2       = edge(1,n);
    m        = fClip(c1);
    if (fClip(c2) > m) m = fClip(c2);
  for (int j=1; j<m+1; j++){
    Ax       = facs(0,j,n);
    Ay       = facs(1,j,n);
    A        = Ax*Ax+Ay*Ay;
    ll(j,c1)+= A;
    ll(j,c2)+= A;
  }}
  int jp;
  for (int n=0; n<nFaces-nGfaces; n++){
  for (int j=0; j<fClip(n)+1; j++){
    jp       = j+1;
    Ax       = facu(0,j,n);
    Ay       = facu(1,j,n);
    A        = Ax*Ax+Ay*Ay;
    ll(j ,n)+= A;
    ll(jp,n)+= A;
  }}


  // CFL and VNN ramping
  double cflT,vnnT;
  if (pseudoStep > nRamp){
    cflT = cfl;
    vnnT = vnn;
  }
  else{
    cflT = cfl0+(cfl-cfl0)/((double)nRamp)*((double)pseudoStep);
    vnnT = vnn0+(vnn-vnn0)/((double)nRamp)*((double)pseudoStep);
  }

  for (int n=0; n<nFaces+nBedges; n++)
  for (int j=0; j<nPstr+2; j++) dt(j,n) = 0;
  if (inviscid == 1){
    for (int n=0; n<nFaces-nGfaces; n++)
    for (int j=0; j<fClip(n)+1; j++) dt(j,n) = radi(j,n)/cflT;
  }
  if (viscous == 1){
    double a;
    for (int n=0; n<nFaces-nGfaces; n++)
    for (int j=0; j<fClip(n)+1; j++){
      a = radv(j,n)/vnnT;
      if (a > dt(j,n)) dt(j,n) = a;
    }
  }
  for (int n=0; n<nFaces-nGfaces; n++)
    //for (int j=0; j<fClip(n)+1; j++) dt(j,n) = ll(j,n)/dt(j,n);
    for (int j=0; j<fClip(n)+1; j++) dt(j,n) = v(j,n)/dt(j,n);


  int jj=1;
  double pj[nq*nq],a;
  for (int n=0; n<nFaces-nGfaces; n++)
  for (int j=0; j<fClip(n)+1; j++){
    sys->lhsPreconJacobian(jj,&q(0,j,n),&qa(0,j,n),&pj[0]);
    a = v(j,n)/dt(j,n);
    for (int k=0; k<nq; k++){
      m = k*nq;
    for (int l=0; l<nq; l++) dd(l,k,j,n) += pj[m+l]*a;
    }}

  ll.deallocate();
}
示例#5
0
void StrandBlockSolver::shiftTime(const int& step,
				  const int& mglevel)
{
  if (mglevel == 0){ // fine MG level
    cout << "\n*** Preparing to solve step " << step << " ***" << endl;
    cout << "physical time " << double(step)*dtUnsteady << endl;
    cout << "time step " << dtUnsteady << endl;


    // advance q, v, and x
    if (step == 1){
      for (int n=0; n<nFaces+nBedges; n++)
	for (int j=0; j<nPstr+2; j++){
	  for (int k=0; k<nq; k++){
	    q1(k,j,n) = q(k,j,n);
	    q2(k,j,n) = q(k,j,n);
	  }
	  v2(j,n) = v(j,n);
	  v1(j,n) = v(j,n);
	}
      for (int n=0; n<nNodes; n++)
	for (int j=0; j<nPstr+1; j++){
	  for (int k=0; k<ndim; k++){
	    x0(k,j,n) = x(k,j,n);
	    x1(k,j,n) = x(k,j,n);
	    x2(k,j,n) = x(k,j,n);
	  }}
    }
    else{
      for (int n=0; n<nFaces+nBedges; n++)
	for (int j=0; j<nPstr+2; j++){
	  for (int k=0; k<nq; k++){
	    q2(k,j,n) = q1(k,j,n);
	    q1(k,j,n) = q(k,j,n);
	  }
	  v2(j,n) = v1(j,n);
	  v1(j,n) = v(j,n);
	}
     for (int n=0; n<nNodes; n++)
	for (int j=0; j<nPstr+1; j++){
	  for (int k=0; k<ndim; k++){
	    x2(k,j,n) = x1(k,j,n);
	    x1(k,j,n) = x(k,j,n);
	    //x(k,j,n) = ?;
	  }}
    }


    // compute face areas, cell-centers, and volumes
    facearea_(pid,
	      ndim,
	      nFaces,
	      nGfaces,
	      nNodes,
	      nGnodes,
	      nEdges,
	      nBedges,
	      nPstr,
	      &face(0,0),
	      &edge(0,0),
	      &edgn(0),
	      &x(0,0,0),
	      &facs(0,0,0),
	      &facu(0,0,0));
    cellcoord_(pid,
	       ndim,
	       nFaces,
	       nGfaces,
	       nNodes,
	       nGnodes,
	       nEdges,
	       nBedges,
	       nPstr,
	       &face(0,0),
	       &edge(0,0),
	       &edgn(0),
	       &x(0,0,0),
	       &facs(0,0,0),
	       &facu(0,0,0),
	       &xc(0,0,0));
    volume_(pid,
	    ndim,
	    nFaces,
	    nGfaces,
	    nNodes,
	    nGnodes,
	    nEdges,
	    nBedges,
	    nPstr,
	    &face(0,0),
	    &edge(0,0),
	    &edgn(0),
	    &fClip(0),
	    &x(0,0,0),
	    &facs(0,0,0),
	    &facu(0,0,0),
	    &xc(0,0,0),
	    &v(0,0));


    // compute least squares coefficients
    if      (nodeVal == 1) lspVol();
    else if (nodeVal == 2) lspLS();
    else if (nodeVal == 3) lspMap();
    else{
      cout << "\nvalue of nodeVal not recognized" << endl;
      exit(0);
    }
  }


  else{ // coarse MG level
    // compute coarse level face areas and volumes
    coarseMetrics();
  }


  // face velocities
  cout << "\n*** face velocity computation not yet implemented ***" << endl;
}
示例#6
0
void StrandBlockSolver::lhsDissipation()
{
  int jj=nPstr+2,nn=nFaces+nBedges;
  Array4D<double> aa(nq,nq,jj,nn);
  for (int n=0; n<nFaces+nBedges; n++)
    for (int j=0; j<nPstr+2; j++)
      for (int k=0; k<nq; k++)
	for (int l=0; l<nq; l++) aa(l,k,j,n) = 0.;


  // unstructured faces
  int c1,c2,n1,n2,jp,fc,m,mm,m1l,m1u,m2l,m2u,npts=1;
  double a[nq*nq];
  for (int n=0; n<nEdges; n++){
    c1            = edge(0,n);
    c2            = edge(1,n);
    m1l           = ncsc(c1  );
    m1u           = ncsc(c1+1);
    m2l           = ncsc(c2  );
    m2u           = ncsc(c2+1);
    fc            = fClip(c1);
    if (fClip(c2) > fc) fc = fClip(c2);
  for (int j=1; j<fc+1; j++){
    sys->lhsDisFluxJacobian(npts,&facs(0,j,n),&xvs(j,n),
			    &q(0,j,c1),&q(0,j,c2),&a[0]);

    for (int k=0; k<nq*nq; k++) a[k] *= .5;

    // diagonal contributions
    for (int k=0; k<nq; k++){
      m             = k*nq;
    for (int l=0; l<nq; l++){
      dd(l,k,j,c1) += a[m+l];
      dd(l,k,j,c2) += a[m+l];
    }}

    // off-diagonal contributions
    for (int k=0; k<nq; k++){
      m             = k*nq;
    for (int l=0; l<nq; l++){
      aa(l,k,j,c1)  = a[m+l];
      aa(l,k,j,c2)  = a[m+l];
    }}

    for (int mm=m1l; mm<m1u; mm++){
      nn            = csc(mm);
      for (int k=0; k<nq; k++){
	m           = k*nq;
      for (int l=0; l<nq; l++)
	bu(l,k,j,mm) -= aa(l,k,j,nn);
      }}

    for (int mm=m2l; mm<m2u; mm++){
      nn            = csc(mm);
      for (int k=0; k<nq; k++){
	m           = k*nq;
      for (int l=0; l<nq; l++)
	bu(l,k,j,mm) -= aa(l,k,j,nn);
      }}

    // reset working array to zero
    for (int k=0; k<nq; k++){
      m             = k*nq;
    for (int l=0; l<nq; l++){
      aa(l,k,j,c1)  = 0.;
      aa(l,k,j,c2)  = 0.;
    }}
  }}

  aa.deallocate();


  // structured faces
  double Ax,Ay,ds,eps=1.e-14;
  for (int n=0; n<nFaces-nGfaces; n++){
    n1            = face(0,n);
    n2            = face(1,n);
  for (int j=0; j<fClip(n)+1; j++){
    jp            = j+1;
    Ax            = facu(0,j,n);
    Ay            = facu(1,j,n);
    ds            = Ax*Ax+Ay*Ay;
    if (fabs(ds) < eps){
      for (int k=0; k<nq; k++){
	m         = k*nq;
      for (int l=0; l<nq; l++)
	a[m+l]    = 0.;
      }}
    else
      sys->lhsDisFluxJacobian(npts,&facu(0,j,n),&xvu(j,n),
			      &q(0,j,n),&q(0,jp,n),&a[0]);
    for (int k=0; k<nq; k++){
      m             = k*nq;
    for (int l=0; l<nq; l++){
      dd(l,k,j ,n) += (a[m+l]*.5);
      dp(l,k,j ,n) -= (a[m+l]*.5);
      dd(l,k,jp,n) += (a[m+l]*.5);
      dm(l,k,jp,n) -= (a[m+l]*.5);
    }}}}
}