Пример #1
0
void AdvanceSolution_Midpoint(Conserved *U, double dt)
{
  int i;

  Conserved *L  = (Conserved*) malloc((Nx+2*Ng)*sizeof(Conserved));
  Conserved *U1 = (Conserved*) malloc((Nx+2*Ng)*sizeof(Conserved));

  SetBoundaryConditions(U);
  TimeDerivative(U, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U1[i].D   = U[i].D   + L[i].D   * 0.5 * dt;
    U1[i].tau = U[i].tau + L[i].tau * 0.5 * dt;
    U1[i].Sx  = U[i].Sx  + L[i].Sx  * 0.5 * dt;
    U1[i].Sy  = U[i].Sy  + L[i].Sy  * 0.5 * dt;
    U1[i].Sz  = U[i].Sz  + L[i].Sz  * 0.5 * dt;
  }

  SetBoundaryConditions(U1);
  TimeDerivative(U1, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U[i].D   = U[i].D   + L[i].D   * dt;
    U[i].tau = U[i].tau + L[i].tau * dt;
    U[i].Sx  = U[i].Sx  + L[i].Sx  * dt;
    U[i].Sy  = U[i].Sy  + L[i].Sy  * dt;
    U[i].Sz  = U[i].Sz  + L[i].Sz  * dt;
  }

  free(L);
  free(U1);
}
    /**
     * Implicit part of the method - Poisson + nConv*Helmholtz
     */
    void VelocityCorrectionScheme::SolveUnsteadyStokesSystem(
        const Array<OneD, const Array<OneD, NekDouble> > &inarray, 
        Array<OneD, Array<OneD, NekDouble> > &outarray, 
        const NekDouble time, 
        const NekDouble aii_Dt)
    {
        int i;
        int phystot = m_fields[0]->GetTotPoints();

        Array<OneD, Array< OneD, NekDouble> > F(m_nConvectiveFields);
        for(i = 0; i < m_nConvectiveFields; ++i)
        {
            F[i] = Array<OneD, NekDouble> (phystot, 0.0);
        }

        // Enforcing boundary conditions on all fields
        SetBoundaryConditions(time);
        
        // Substep the pressure boundary condition if using substepping
        m_extrapolation->SubStepSetPressureBCs(inarray,aii_Dt,m_kinvis);
    
        // Set up forcing term for pressure Poisson equation
        SetUpPressureForcing(inarray, F, aii_Dt);

        // Solve Pressure System
        SolvePressure (F[0]);

        // Set up forcing term for Helmholtz problems
        SetUpViscousForcing(inarray, F, aii_Dt);
        
        // Solve velocity system
        SolveViscous( F, outarray, aii_Dt);
    }
Пример #3
0
    void EulerADCFE::DoOdeProjection(
        const Array<OneD, const Array<OneD, NekDouble> > &inarray,
        Array<OneD,       Array<OneD, NekDouble> > &outarray,
        const NekDouble                                   time)
    {
        int i;
        int nvariables = inarray.num_elements();

        switch(m_projectionType)
        {
            case MultiRegions::eDiscontinuous:
            {
                // Just copy over array
                int npoints = GetNpoints();

                for(i = 0; i < nvariables; ++i)
                {
                    Vmath::Vcopy(npoints, inarray[i], 1, outarray[i], 1);
                }
                SetBoundaryConditions(outarray, time);
                break;
            }
            case MultiRegions::eGalerkin:
            case MultiRegions::eMixed_CG_Discontinuous:
            {
                ASSERTL0(false, "No Continuous Galerkin for Euler equations");
                break;
            }
            default:
                ASSERTL0(false, "Unknown projection scheme");
                break;
        }
    }
Пример #4
0
    /**
     *	Does the projection between ... space and the ... space. Also checks for Q-inflow boundary 
     *  conditions at the inflow of the current arterial segment and applies the Q-inflow if specified
     */
    void PulseWavePropagation::SetPulseWaveBoundaryConditions(
        const Array<OneD,const Array<OneD, NekDouble> >&inarray, 
        Array<OneD, Array<OneD, NekDouble> >&outarray, 
        const NekDouble time)
        
    {
        int omega;
        
        Array<OneD, MultiRegions::ExpListSharedPtr>     vessel(2);

        int offset=0; 

        //This will be moved to the RCR boundary condition once factory is setup
	if (time == 0)
        {
            m_Boundary = Array<OneD,PulseWaveBoundarySharedPtr>(2*m_nDomains);

            for(omega = 0; omega < m_nDomains; ++omega)
            {
                vessel[0] = m_vessels[2*omega];

                for(int j = 0; j < 2; ++j)
                {	
                    std::string BCType =vessel[0]->GetBndConditions()[j]->GetUserDefined();
                    if(BCType.empty()) // if not condition given define it to be NoUserDefined
                    {
                        BCType = "NoUserDefined";
                    }

                    m_Boundary[2*omega+j]=GetBoundaryFactory().CreateInstance(BCType,m_vessels,m_session,m_pressureArea);
                    
                    // turn on time depedent BCs 
                    if(BCType == "Q-inflow")
                    {
                        vessel[0]->GetBndConditions()[j]->SetIsTimeDependent(true);
                    }
                    else if(BCType == "RCR-terminal")
                    {
                        vessel[0]->GetBndConditions()[j]->SetIsTimeDependent(true);
                    }
                }
            }

        }

        SetBoundaryConditions(time);

        // Loop over all vessesls and set boundary conditions
        for(omega = 0; omega < m_nDomains; ++omega)
        {
            for(int n = 0; n < 2; ++n)
            {	
                m_Boundary[2*omega+n]->DoBoundary(inarray,m_A_0,m_beta,time,omega,offset,n);
            }
            offset += m_vessels[2*omega]->GetTotPoints();
        }

    }
Пример #5
0
void AdvanceSolution_ShuOsher(Conserved *U, double dt)
{
  int i;

  Conserved *L  = (Conserved*) malloc((Nx+2*Ng)*sizeof(Conserved));
  Conserved *U1 = (Conserved*) malloc((Nx+2*Ng)*sizeof(Conserved));

  SetBoundaryConditions(U);
  TimeDerivative(U, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U1[i].D   = U[i].D   + L[i].D   * dt;
    U1[i].tau = U[i].tau + L[i].tau * dt;
    U1[i].Sx  = U[i].Sx  + L[i].Sx  * dt;
    U1[i].Sy  = U[i].Sy  + L[i].Sy  * dt;
    U1[i].Sz  = U[i].Sz  + L[i].Sz  * dt;
  }

  SetBoundaryConditions(U1);
  TimeDerivative(U1, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U1[i].D   = 3./4. * U[i].D   + 1./4. * U1[i].D   + 1./4. * L[i].D   * dt;
    U1[i].tau = 3./4. * U[i].tau + 1./4. * U1[i].tau + 1./4. * L[i].tau * dt;
    U1[i].Sx  = 3./4. * U[i].Sx  + 1./4. * U1[i].Sx  + 1./4. * L[i].Sx  * dt;
    U1[i].Sy  = 3./4. * U[i].Sy  + 1./4. * U1[i].Sy  + 1./4. * L[i].Sy  * dt;
    U1[i].Sz  = 3./4. * U[i].Sz  + 1./4. * U1[i].Sz  + 1./4. * L[i].Sz  * dt;
  }

  SetBoundaryConditions(U1);
  TimeDerivative(U1, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U[i].D   = 1./3. * U[i].D   + 2./3. * U1[i].D   + 2./3. * L[i].D   * dt;
    U[i].tau = 1./3. * U[i].tau + 2./3. * U1[i].tau + 2./3. * L[i].tau * dt;
    U[i].Sx  = 1./3. * U[i].Sx  + 2./3. * U1[i].Sx  + 2./3. * L[i].Sx  * dt;
    U[i].Sy  = 1./3. * U[i].Sy  + 2./3. * U1[i].Sy  + 2./3. * L[i].Sy  * dt;
    U[i].Sz  = 1./3. * U[i].Sz  + 2./3. * U1[i].Sz  + 2./3. * L[i].Sz  * dt;
  }

  free(L);
  free(U1);
}
Пример #6
0
    /**
     * @brief Compute the projection for the linear advection equation.
     *
     * @param inarray    Given fields.
     * @param outarray   Calculated solution.
     * @param time       Time.
     */
    void UnsteadyAdvection::DoOdeProjection(
        const Array<OneD, const Array<OneD, NekDouble> >&inarray,
              Array<OneD,       Array<OneD, NekDouble> >&outarray,
        const NekDouble time)
    {
        // Counter variable
        int i;

        // Number of fields (variables of the problem)
        int nVariables = inarray.num_elements();

        // Set the boundary conditions
        SetBoundaryConditions(time);

        // Switch on the projection type (Discontinuous or Continuous)
        switch(m_projectionType)
        {
            // Discontinuous projection
            case MultiRegions::eDiscontinuous:
            {
                // Number of quadrature points
                int nQuadraturePts = GetNpoints();

                // Just copy over array
                for(i = 0; i < nVariables; ++i)
                {
                    Vmath::Vcopy(nQuadraturePts, inarray[i], 1, outarray[i], 1);
                }
                break;
            }

            // Continuous projection
            case MultiRegions::eGalerkin:
            case MultiRegions::eMixed_CG_Discontinuous:
            {
                Array<OneD, NekDouble> coeffs(m_fields[0]->GetNcoeffs(),0.0);
                for(i = 0; i < nVariables; ++i)
                {
                    m_fields[i]->FwdTrans(inarray[i], coeffs);
                    m_fields[i]->BwdTrans_IterPerExp(coeffs, outarray[i]);
                }
                break;
            }

            default:
                ASSERTL0(false,"Unknown projection scheme");
                break;
        }
    }
Пример #7
0
/**
 * @brief Compute the projection and call the method for imposing the
 * boundary conditions in case of discontinuous projection.
 */
void APE::DoOdeProjection(const Array<OneD, const Array<OneD, NekDouble> >&inarray,
                                Array<OneD,       Array<OneD, NekDouble> >&outarray,
                          const NekDouble time)
{
    int nvariables = inarray.num_elements();
    int nq = m_fields[0]->GetNpoints();

    // deep copy
    for (int i = 0; i < nvariables; ++i)
    {
        Vmath::Vcopy(nq, inarray[i], 1, outarray[i], 1);
    }

    SetBoundaryConditions(outarray, time);
}
Пример #8
0
void AdvanceSolution_FwdEuler(Conserved *U, double dt)
{
  int i;

  Conserved *L  = (Conserved*) malloc((Nx+2*Ng)*sizeof(Conserved));

  SetBoundaryConditions(U);
  TimeDerivative(U, L);

  for (i=0; i<Nx+2*Ng; ++i) {
    U[i].D   += L[i].D   * dt;
    U[i].tau += L[i].tau * dt;
    U[i].Sx  += L[i].Sx  * dt;
    U[i].Sy  += L[i].Sy  * dt;
    U[i].Sz  += L[i].Sz  * dt;
  }

  free(L);
}
    void VelocityCorrectionScheme::v_DoInitialise(void)
    {

        UnsteadySystem::v_DoInitialise();

        // Set up Field Meta Data for output files
        m_fieldMetaDataMap["Kinvis"]   = boost::lexical_cast<std::string>(m_kinvis);
        m_fieldMetaDataMap["TimeStep"] = boost::lexical_cast<std::string>(m_timestep);

        // set boundary conditions here so that any normal component
        // correction are imposed before they are imposed on intiial
        // field below
        SetBoundaryConditions(m_time);

        for(int i = 0; i < m_nConvectiveFields; ++i)
        {
            m_fields[i]->LocalToGlobal();
            m_fields[i]->ImposeDirichletConditions(m_fields[i]->UpdateCoeffs());
            m_fields[i]->GlobalToLocal();
            m_fields[i]->BwdTrans(m_fields[i]->GetCoeffs(),
                                  m_fields[i]->UpdatePhys());
        }
    }