Beispiel #1
0
double oper::divVCJH_quad(int in_fpt, vector<double>& loc, vector<double>& loc_1d_spts, uint vcjh, uint order)
{
  uint i,j;
  double eta;
  double div_vcjh_basis = 0;

  if (vcjh == DG)
    eta = 0.; // HiFiLES: run_input.eta_quad;
  else
    eta = compute_eta(vcjh,order);

  i = in_fpt / (order+1);      // Face upon which the flux point lies [0,1,2, or 3]
  j = in_fpt - (order+1)*i;    // Face-local index of flux point [0 to n_fpts_per_face-1]

  if(i==0)
    div_vcjh_basis = -Lagrange(loc_1d_spts,loc[0],j) * dVCJH_1d(loc[1],0,order,eta); // was -'ve
  else if(i==1)
    div_vcjh_basis =  Lagrange(loc_1d_spts,loc[1],j) * dVCJH_1d(loc[0],1,order,eta);
  else if(i==2)
    div_vcjh_basis =  Lagrange(loc_1d_spts,loc[0],order-j) * dVCJH_1d(loc[1],1,order,eta);
  else if(i==3)
    div_vcjh_basis =-Lagrange(loc_1d_spts,loc[1],order-j) * dVCJH_1d(loc[0],0,order,eta); // was -'ve


  return div_vcjh_basis;
}
Beispiel #2
0
void step(HashTable* El_Table, HashTable* NodeTable, int myid, int nump,
          MatProps* matprops_ptr, TimeProps* timeprops_ptr,
          PileProps *pileprops_ptr, FluxProps *fluxprops,
          StatProps* statprops_ptr, int* order_flag,
          OutLine* outline_ptr, DISCHARGE* discharge, int adaptflag)
{
    /*
     * PREDICTOR-CORRECTED based on Davis' Simplified Godunov Method
     */

    /* pass off proc data here (really only need state_vars for off-proc neighbors) */
    move_data(nump, myid, El_Table, NodeTable,timeprops_ptr);

    slopes(El_Table, NodeTable, matprops_ptr);

    // get coefficients, eigenvalues, hmax and calculate the time step
    double dt = get_coef_and_eigen(El_Table, NodeTable, matprops_ptr,
                                   fluxprops, timeprops_ptr,0);

    timeprops_ptr->incrtime(&dt); //also reduces dt if necessary

    // assign influxes and then if any new sources are activating in
    // current time step refine and re-mark cells
    adapt_fluxsrc_region(El_Table,NodeTable,matprops_ptr,pileprops_ptr,fluxprops,
                         timeprops_ptr,dt,myid,adaptflag);

    int i;

    HashEntryPtr* buck = El_Table->getbucketptr();
    HashEntryPtr currentPtr;
    Element* Curr_El;

    double dt2 = .5*dt; // dt2 is set as dt/2 !
    // printf("dt for explicit is ...%f \n", dt);

    /*
     *  predictor step
     */
    int j,k, counter;
    double tiny = GEOFLOW_TINY,phi;
    double flux_src_coef=0;

    // printf("the number of elements are ...........%d\n", num_nonzero_elem(El_Table));
#ifdef SECOND_ORDER
    //-------------------go through all the elements of the subdomain and
    //-------------------calculate the state variables at time .5*delta_t
    /* mdj 2007-04 */
    int IF_STOPPED;
    double curr_time,influx[3],*d_uvec,*lap_phi; //VxVy[2];
    double VxVy[2];
    Node* nd;
    #pragma omp parallel for                                                \
    private(currentPtr,Curr_El,IF_STOPPED,influx,j,k,curr_time,flux_src_coef,VxVy)
    for(i=0; i<El_Table->get_no_of_buckets(); i++)
        if(*(buck+i))
        {
            currentPtr = *(buck+i);
            while(currentPtr) {

                Curr_El=(Element*)(currentPtr->value);

                influx[3];
                influx[0]=*(Curr_El->get_influx()+0);
                influx[1]=*(Curr_El->get_influx()+1);
                influx[2]=*(Curr_El->get_influx()+2);

                if(!(influx[0]>=0.0)) {
                    printf("negative influx=%g\n",influx[0]);
                    assert(0);
                }


                if(Curr_El->get_adapted_flag()>0) {
                    lap_phi=Curr_El->get_lap_phi();
                    d_uvec = Curr_El->get_d_state_vars();
                    nd = (Node*) NodeTable->lookup(Curr_El->pass_key());

                    // -- calc contribution of flux source
                    flux_src_coef=0;
                    curr_time=(timeprops_ptr->time)*(timeprops_ptr->TIME_SCALE);

                    //VxVy[2];
                    if(*(Curr_El->get_state_vars())>0/*GEOFLOW_TINY*/) {
                        VxVy[0]=*(Curr_El->get_state_vars()+2)/ *(Curr_El->get_state_vars()+1);
                        VxVy[1]=*(Curr_El->get_state_vars()+3)/ *(Curr_El->get_state_vars()+1);
                    }
                    else
                        VxVy[0]=VxVy[1]=0.0;

#ifdef STOPCRIT_CHANGE_SOURCE
                    IF_STOPPED=Curr_El->get_stoppedflags();
#else
                    IF_STOPPED=!(!(Curr_El->get_stoppedflags()));
#endif

                    predict_(Curr_El->get_state_vars(), d_uvec, (d_uvec+NUM_STATE_VARS),lap_phi,
                             Curr_El->get_prev_state_vars(), &tiny,
                             Curr_El->get_kactxy(), &dt2, Curr_El->get_gravity(),
                             Curr_El->get_curvature(),
                             &(matprops_ptr->bedfrict[Curr_El->get_material()]),
                             &(matprops_ptr->intfrict),
                             Curr_El->get_d_gravity(), &(matprops_ptr->frict_tiny),
                             order_flag, VxVy,
                             &IF_STOPPED,influx);

                    /* apply bc's */
#ifdef APPLY_BC
                    for(j=0; j<4; j++)
                        if(*(Curr_El->get_neigh_proc()+j) == INIT)   // this is a boundary!
                            for(k=1; k<NUM_STATE_VARS; k++)
                                *(Curr_El->get_state_vars()+k) = 0;
#endif
                }
                currentPtr=currentPtr->next;
            }
        }
    /* finished predictor step */
    /* really only need to share dudx, state_vars, and kactxy */
    move_data(nump, myid, El_Table, NodeTable,timeprops_ptr);

    /* calculate the slopes for the new (half-time step) state variables */
    slopes(El_Table, NodeTable, matprops_ptr);
#endif  //SECOND_ORDER

    /* really only need to share dudx, state_vars, and kactxy */
    move_data(nump, myid, El_Table, NodeTable,timeprops_ptr);

    /* calculate kact/pass */
    double dt_not_used = get_coef_and_eigen(El_Table, NodeTable, matprops_ptr,
                                            fluxprops, timeprops_ptr, 1);

    /*
     * calculate edge states
     */
    double outflow=0.0;  //shouldn't need the =0.0 assignment but just being cautious.
    //printf("step: before calc_edge_states\n"); fflush(stdout);
    calc_edge_states(El_Table,NodeTable,matprops_ptr,timeprops_ptr,myid,order_flag,&outflow);

    //printf("the outflow in step after calc_edge ..............%f\n",outflow);
    outflow*=dt;
    //printf("the dt in step ...............%f\n",dt);
    //printf("the outflow in step ...............%f\n",outflow);

    MapNames mapnames;
    char *b,*c,*d;
    char a[5]="abs";// ,b[5],c[5],d[5];
    b=c=d=a;
    int ce=0;

    mapnames.assign(a, b, c,d, ce);

//  if (/*timeprops_ptr->iter%50==4||*/timeprops_ptr->iter==1){
//    int tt=timeprops_ptr->iter;
    //for(int ii=0;ii<1000;ii++){

//      initialization( NodeTable, El_Table, dt, matprops_ptr,fluxprops, timeprops_ptr);
//      meshplotter(El_Table, NodeTable,matprops_ptr,timeprops_ptr,&mapnames,ce);
    //timeprops_ptr->iter++;
    //}
    //timeprops_ptr->iter=tt;
//  }


    /*
     * corrector step and b.c.s
     */

    //for comparison of magnitudes of forces in slumping piles
    double forceint=0.0, elemforceint;
    double forcebed=0.0, elemforcebed;
    double eroded=0.0, elemeroded;
    double deposited=0.0, elemdeposited;
    double realvolume=0.0;

    double eta=compute_eta(El_Table,statprops_ptr );

    for(i=0; i<El_Table->get_no_of_buckets(); i++)
        if(*(buck+i))
        {
            HashEntryPtr currentPtr = *(buck+i);
            while(currentPtr)
            {
                Element* Curr_El=(Element*)(currentPtr->value);
                if(Curr_El->get_adapted_flag()>0) { //if this is a refined element don't involve!!!

                    double *dxy=Curr_El->get_dx();
                    // if calculations are first-order, predict is never called
                    // ... so we need to update prev_states
                    // double phi=*(Curr_El->get_state_vars())+*(Curr_El->get_state_vars()+4);

                    if ( *order_flag == 1 )
                        Curr_El->update_prev_state_vars();

                    void *Curr_El_out= (void *) Curr_El;

                    correct(NodeTable, El_Table, dt, matprops_ptr,
                            fluxprops, timeprops_ptr,
                            Curr_El_out,
                            &elemforceint,&elemforcebed,
                            &elemeroded,&elemdeposited,&eta);

                    for(int kk=0; kk<6; kk++)
                        if (isnan(*(Curr_El->get_state_vars()+kk)))
                            printf("Hello this is the NAN");
                    forceint+=fabs(elemforceint);
                    forcebed+=fabs(elemforcebed);
                    realvolume+=dxy[0]*dxy[1]**(Curr_El->get_state_vars()+1);
                    eroded+=elemeroded;
                    deposited+=elemdeposited;

                    double *coord=Curr_El->get_coord();
                    //update the record of maximum pileheight in the area covered by this element
                    double hheight;
                    if(*(Curr_El->get_state_vars())>=0)   hheight=*(Curr_El->get_state_vars()+1);
                    else hheight=0;
                    if(hheight>0 && hheight<0);


#ifdef MAX_DEPTH_MAP
                    double pfheight[6];
                    outline_ptr->update(coord[0]-0.5*dxy[0],coord[0]+0.5*dxy[0],
                                        coord[1]-0.5*dxy[1],coord[1]+0.5*dxy[1],
                                        hheight,pfheight);
#endif

#ifdef APPLY_BC
                    for(j=0; j<4; j++)
                        if(*(Curr_El->get_neigh_proc()+j) == INIT)   // this is a boundary!
                            for(k=1; k<NUM_STATE_VARS; k++)
                                *(Curr_El->get_state_vars()+k) = 0;
#endif
                }
                currentPtr=currentPtr->next;
            }
        }
    double timedelta=0;
    // ====================================================Implicit Solver==========================
    if (timeprops_ptr->iter%5==4 ||timeprops_ptr->iter==1 || timeprops_ptr->time>=timeprops_ptr->ndnextoutput  /*|| timeprops_ptr->iter==1 */) { //{|| timeprops_ptr->iter == 1){//|| timeprops_ptr->iter % 5 ==2){
        timedelta= (timeprops_ptr->time-timeprops_ptr->implicit);//*timeprops_ptr->TIME_SCALE;
        LaplacianData  Laplacian (El_Table, NodeTable , timedelta, .0001,timeprops_ptr);

//cout<<"time data not scaled  "<<timeprops_ptr->time-timeprops_ptr->implicit<<"   scaled time is   "<<timedelta<<"  Time Scale is "<<timeprops_ptr->TIME_SCALE<<endl;

        timeprops_ptr->implicit = timeprops_ptr->time;

        implicit_solver(&Laplacian);

    }

    for(i=0; i<El_Table->get_no_of_buckets(); i++) {
        if(*(buck+i))
        {
            HashEntryPtr currentPtr = *(buck+i);
            while(currentPtr)
            {
                Element* Curr_El=(Element*)(currentPtr->value);
                if(Curr_El->get_adapted_flag()>0
                  )//&& ((timeprops_ptr->iter%5==4)))//||(timeprops_ptr->iter%5==2)))
                {   //if this is a refined element don't involve!!!
//  		//if (*(Curr_El->get_state_vars()+1)>1e-3)
//		//{
                    phi = *(Curr_El->get_state_vars());
                    if(phi*timeprops_ptr->TIME_SCALE>1) phi=1/timeprops_ptr->TIME_SCALE;
                    if(phi*timeprops_ptr->TIME_SCALE<-1) phi=-1/timeprops_ptr->TIME_SCALE;
                    //}
                    //else
                    //phi=0;
                    *(Curr_El->get_state_vars())=phi;
                    //  		Curr_El->update_phase1(phi);
                }
                currentPtr=currentPtr->next;
            }
        }
    }

    //update the orientation of the "dryline" (divides partially wetted cells
    //into wet and dry parts solely based on which neighbors currently have
    //pileheight greater than GEOFLOW_TINY
    //for(i=0; i<El_Table->get_no_of_buckets(); i++)
    // {
    //     HashEntryPtr currentPtr = *(buck+i);
    //    while(currentPtr)
//	{
//	  Element* Curr_El=(Element*)(currentPtr->value);
//	  currentPtr=currentPtr->next;
//	  if(Curr_El->get_adapted_flag()>0) //if this is a refined element don't involve!!!
//	    Curr_El->calc_wet_dry_orient(El_Table);
//	}
    //  }

    /* finished corrector step */
    calc_stats(El_Table, NodeTable, myid, matprops_ptr, timeprops_ptr,
               statprops_ptr, discharge, dt);

    double tempin[6], tempout[6];
    tempin[0]=outflow;    //volume that flew out the boundaries this iteration
    tempin[1]=eroded;     //volume that was eroded this iteration
    tempin[2]=deposited;  //volume that is currently deposited
    tempin[3]=realvolume; //"actual" volume within boundaries
    tempin[4]=forceint;   //internal friction force
    tempin[5]=forcebed;   //bed friction force

    MPI_Reduce(tempin,tempout,6,MPI_DOUBLE,MPI_SUM,0,MPI_COMM_WORLD);

    statprops_ptr->outflowvol+=tempout[0]*(matprops_ptr->HEIGHT_SCALE)*
                               (matprops_ptr->LENGTH_SCALE)*(matprops_ptr->LENGTH_SCALE);
    statprops_ptr->erodedvol+=tempout[1]*(matprops_ptr->HEIGHT_SCALE)*
                              (matprops_ptr->LENGTH_SCALE)*(matprops_ptr->LENGTH_SCALE);
    statprops_ptr->depositedvol=tempout[2]*(matprops_ptr->HEIGHT_SCALE)*
                                (matprops_ptr->LENGTH_SCALE)*(matprops_ptr->LENGTH_SCALE);
    statprops_ptr->realvolume=tempout[3]*(matprops_ptr->HEIGHT_SCALE)*
                              (matprops_ptr->LENGTH_SCALE)*(matprops_ptr->LENGTH_SCALE);

    statprops_ptr->forceint=tempout[4]/tempout[3]*matprops_ptr->GRAVITY_SCALE;
    statprops_ptr->forcebed=tempout[5]/tempout[3]*matprops_ptr->GRAVITY_SCALE;

    return;
}