Ignore:
Timestamp:
05/09/14 14:51:29 (11 years ago)
Author:
Mathieu Morlighem
Message:

CHG: moving misfits to modules

File:
1 edited

Legend:

Unmodified
Added
Removed
  • issm/trunk-jpl/src/c/modules/SurfaceRelVelMisfitx/SurfaceRelVelMisfitx.cpp

    r16314 r17975  
    1010void SurfaceRelVelMisfitx( IssmDouble* pJ, Elements* elements,Nodes* nodes, Vertices* vertices, Loads* loads, Materials* materials,Parameters* parameters){
    1111
    12         /*Intermediary*/
    13         int i;
    14         Element* element=NULL;
    15 
    1612        /*output: */
    17         IssmDouble J=0;
     13        IssmDouble J=0.;
    1814        IssmDouble J_sum;
    1915
    2016        /*Compute Misfit: */
    21         for (i=0;i<elements->Size();i++){
    22                 element=dynamic_cast<Element*>(elements->GetObjectByOffset(i));
    23                 J+=element->SurfaceRelVelMisfit();
     17        for(int i=0;i<elements->Size();i++){
     18                Element* element=dynamic_cast<Element*>(elements->GetObjectByOffset(i));
     19                J+=SurfaceRelVelMisfit(element);
    2420        }
    2521
     
    3228        *pJ=J;
    3329}
     30
     31IssmDouble SurfaceRelVelMisfit(Element* element){
     32
     33        int        domaintype,numcomponents;
     34        bool       surfaceintegral;
     35        IssmDouble Jelem=0.;
     36        IssmDouble misfit,Jdet,scalex,scaley;
     37        IssmDouble epsvel=2.220446049250313e-16;
     38        IssmDouble meanvel=3.170979198376458e-05; /*1000 m/yr*/
     39        IssmDouble vx,vy,vxobs,vyobs,weight;
     40        IssmDouble* xyz_list = NULL;
     41
     42        /*Get basal element*/
     43        if(!element->IsOnSurface()) return 0.;
     44
     45        /*If on water, return 0: */
     46        if(!element->IsIceInElement()) return 0.;
     47
     48        /*Get problem dimension*/
     49        element->FindParam(&domaintype,DomainTypeEnum);
     50        switch(domaintype){
     51                case Domain2DverticalEnum:
     52                        surfaceintegral = true;
     53                        numcomponents   = 1;
     54                        break;
     55                case Domain3DEnum:
     56                        surfaceintegral = true;
     57                        numcomponents   = 2;
     58                        break;
     59                case Domain2DhorizontalEnum:
     60                        surfaceintegral = false;
     61                        numcomponents   = 2;
     62                        break;
     63                default: _error_("not supported yet");
     64        }
     65
     66        /*Spawn surface element*/
     67        Element* topelement = element->SpawnTopElement();
     68
     69        /* Get node coordinates*/
     70        topelement->GetVerticesCoordinates(&xyz_list);
     71
     72        /*Retrieve all inputs we will be needing: */
     73        Input* weights_input=topelement->GetInput(InversionCostFunctionsCoefficientsEnum); _assert_(weights_input);
     74        Input* vx_input     =topelement->GetInput(VxEnum);                                 _assert_(vx_input);
     75        Input* vxobs_input  =topelement->GetInput(InversionVxObsEnum);                     _assert_(vxobs_input);
     76        Input* vy_input     = NULL;
     77        Input* vyobs_input  = NULL;
     78        if(numcomponents==2){
     79                vy_input    =topelement->GetInput(VyEnum);              _assert_(vy_input);
     80                vyobs_input =topelement->GetInput(InversionVyObsEnum);  _assert_(vyobs_input);
     81        }
     82
     83        /* Start  looping on the number of gaussian points: */
     84        Gauss* gauss=topelement->NewGauss(4);
     85        for(int ig=gauss->begin();ig<gauss->end();ig++){
     86
     87                gauss->GaussPoint(ig);
     88
     89                /* Get Jacobian determinant: */
     90                topelement->JacobianDeterminant(&Jdet,xyz_list,gauss);
     91
     92                /*Get all parameters at gaussian point*/
     93                weights_input->GetInputValue(&weight,gauss,SurfaceRelVelMisfitEnum);
     94                vx_input->GetInputValue(&vx,gauss);
     95                vxobs_input->GetInputValue(&vxobs,gauss);
     96                if(numcomponents==2){
     97                        vy_input->GetInputValue(&vy,gauss);
     98                        vyobs_input->GetInputValue(&vyobs,gauss);
     99                }
     100
     101                /*Compute SurfaceRelVelMisfit:
     102                 *                       
     103                 *      1  [     \bar{v}^2             2   \bar{v}^2              2 ]
     104                 * J = --- | -------------  (u - u   ) + -------------  (v - v   )  |
     105                 *      2  [  (u   + eps)^2       obs    (v   + eps)^2       obs    ]
     106                 *              obs                        obs                     
     107                 */
     108
     109                if(numcomponents==2){
     110                        scalex=pow(meanvel/(vxobs+epsvel),2); if(vxobs==0)scalex=0;
     111                        scaley=pow(meanvel/(vyobs+epsvel),2); if(vyobs==0)scaley=0;
     112                        misfit=0.5*(scalex*pow((vx-vxobs),2)+scaley*pow((vy-vyobs),2));
     113                }
     114                else{
     115                        scalex=pow(meanvel/(vxobs+epsvel),2); if(vxobs==0)scalex=0;
     116                        misfit=0.5*(scalex*pow((vx-vxobs),2));
     117                }
     118
     119                /*Add to cost function*/
     120                Jelem+=misfit*weight*Jdet*gauss->weight;
     121        }
     122
     123        /*clean up and Return: */
     124        if(domaintype!=Domain2DhorizontalEnum){topelement->DeleteMaterials(); delete topelement;};
     125        xDelete<IssmDouble>(xyz_list);
     126        delete gauss;
     127        return Jelem;
     128}
Note: See TracChangeset for help on using the changeset viewer.