Changeset 8381


Ignore:
Timestamp:
Apr 3, 2012, 7:45:42 AM (13 years ago)
Author:
steve
Message:

Reorganised the compute_fluxes to incorporate teh gravity terms, and to
have the ability to change method. 3 methods now. ome of the unit test are failing
but will fix those up once I get to work. The code seems to be working ok

Location:
trunk
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/anuga_core/source/anuga/shallow_water/shallow_water_domain.py

    r8380 r8381  
    140140            other_quantities = ['elevation', 'friction', 'height',
    141141                                'xvelocity', 'yvelocity', 'x', 'y']
     142
     143
    142144       
    143145       
     
    167169
    168170        #-------------------------------
    169         # Operators and Forcing Terms
     171        # Forcing Terms
     172        #
     173        # Gravity is now incorporated in
     174        # compute_fluxes routine
    170175        #-------------------------------
    171176        self.forcing_terms.append(manning_friction_implicit)
    172         #self.forcing_terms.append(gravity_wb)
    173         self.forcing_terms.append(gravity)
    174 
    175 
    176 
     177
     178
     179        #-------------------------------
     180        # Operators
     181        #-------------------------------
    177182        self.fractional_step_operators = []
    178183        self.kv_operator = None
     
    250255        self.use_centroid_velocities = use_centroid_velocities
    251256
     257
    252258        self.set_compute_fluxes_method(compute_fluxes_method)
    253259
     
    285291           'well_balanced_1
    286292        """
    287         compute_fluxes_methods = ['original', 'well_balanced_1']
     293        compute_fluxes_methods = ['original', 'wb_1', 'wb_2']
    288294
    289295        if flag in compute_fluxes_methods:
     
    295301
    296302
     303
     304
     305
    297306    def get_compute_fluxes_method(self):
    298307        """Get method for computing fluxes.
     
    304313
    305314        return self.compute_fluxes_method
     315
     316
     317    def set_gravity_method(self):
     318        """Gravity method is determined by the compute_fluxes_method
     319        """
     320
     321        if  self.get_compute_fluxes_method() == 'original':
     322            self.forcing_terms[0] = gravity
     323
     324        elif self.get_compute_fluxes_method() == 'wb_1':
     325            self.forcing_terms[0] = gravity_wb
     326
     327        elif self.get_compute_fluxes_method() == 'wb_2':
     328            self.forcing_terms[0] = gravity
     329
     330        else:
     331            raise Exception('undefined compute_fluxes method')
    306332
    307333
     
    625651        if self.compute_fluxes_method == 'original':
    626652            from shallow_water_ext import compute_fluxes_ext_central_structure
     653            from shallow_water_ext import gravity as gravity_c
     654
    627655            self.flux_timestep = compute_fluxes_ext_central_structure(self)
    628         elif self.compute_fluxes_method == 'well_balanced_1':
     656            gravity_c(self)
     657
     658
     659        elif self.compute_fluxes_method == 'wb_1':
    629660            from shallow_water_ext import compute_fluxes_ext_wb
     661            from shallow_water_ext import gravity as gravity_c
     662
    630663            self.flux_timestep = compute_fluxes_ext_wb(self)
     664            gravity_c(self)
     665
     666        elif self.compute_fluxes_method == 'wb_2':
     667            from shallow_water_ext import compute_fluxes_ext_central_structure
     668            from shallow_water_ext import gravity_wb as gravity_wb_c
     669
     670            self.flux_timestep = compute_fluxes_ext_central_structure(self)
     671            gravity_wb_c(self)
     672
    631673        else:
    632674            raise Exception('unknown compute_fluxes_method')
     675
     676
    633677
    634678
     
    10871131       
    10881132        return message       
    1089            
     1133         
     1134
     1135
    10901136################################################################################
    10911137# End of class Shallow Water Domain
     
    10961142#-----------------
    10971143
    1098 def compute_fluxes(domain):
    1099     """Compute fluxes and timestep suitable for all volumes in domain.
    1100 
    1101     Compute total flux for each conserved quantity using "flux_function"
    1102 
    1103     Fluxes across each edge are scaled by edgelengths and summed up
    1104     Resulting flux is then scaled by area and stored in
    1105     explicit_update for each of the three conserved quantities
    1106     stage, xmomentum and ymomentum
    1107 
    1108     The maximal allowable speed computed by the flux_function for each volume
    1109     is converted to a timestep that must not be exceeded. The minimum of
    1110     those is computed as the next overall timestep.
    1111 
    1112     Post conditions:
    1113       domain.explicit_update is reset to computed flux values
    1114       domain.timestep is set to the largest step satisfying all volumes.
    1115 
    1116     This wrapper calls the underlying C version of compute fluxes
    1117     """
    1118 
    1119     import sys
    1120     from shallow_water_ext import compute_fluxes_ext_central \
    1121                                   as compute_fluxes_ext
    1122 
    1123     # Shortcuts
    1124     Stage = domain.quantities['stage']
    1125     Xmom = domain.quantities['xmomentum']
    1126     Ymom = domain.quantities['ymomentum']
    1127     Bed = domain.quantities['elevation']
    1128 
    1129 
    1130 
    1131     timestep = float(sys.maxint)
    1132 
    1133     flux_timestep = compute_fluxes_ext(timestep,
    1134                                        domain.epsilon,
    1135                                        domain.H0,
    1136                                        domain.g,
    1137                                        domain.neighbours,
    1138                                        domain.neighbour_edges,
    1139                                        domain.normals,
    1140                                        domain.edgelengths,
    1141                                        domain.radii,
    1142                                        domain.areas,
    1143                                        domain.tri_full_flag,
    1144                                        Stage.edge_values,
    1145                                        Xmom.edge_values,
    1146                                        Ymom.edge_values,
    1147                                        Bed.edge_values,
    1148                                        Stage.boundary_values,
    1149                                        Xmom.boundary_values,
    1150                                        Ymom.boundary_values,
    1151                                        Stage.explicit_update,
    1152                                        Xmom.explicit_update,
    1153                                        Ymom.explicit_update,
    1154                                        domain.already_computed_flux,
    1155                                        domain.max_speed,
    1156                                        domain.optimise_dry_cells)
    1157 
    1158     domain.flux_timestep = flux_timestep
    1159 
    1160 
    1161 
    1162 def compute_fluxes_structure(domain):
    1163     """Compute fluxes and timestep suitable for all volumes in domain.
    1164 
    1165     Compute total flux for each conserved quantity using "flux_function"
    1166 
    1167     Fluxes across each edge are scaled by edgelengths and summed up
    1168     Resulting flux is then scaled by area and stored in
    1169     explicit_update for each of the three conserved quantities
    1170     stage, xmomentum and ymomentum
    1171 
    1172     The maximal allowable speed computed by the flux_function for each volume
    1173     is converted to a timestep that must not be exceeded. The minimum of
    1174     those is computed as the next overall timestep.
    1175 
    1176     Post conditions:
    1177       domain.explicit_update is reset to computed flux values
    1178       domain.flux_timestep is set to the largest step satisfying all volumes.
    1179 
    1180     This wrapper calls the underlying C version of compute fluxes
    1181     """
    1182 
    1183 
    1184     from shallow_water_ext import compute_fluxes_ext_central_structure
    1185 
    1186 
    1187     domain.flux_timestep = compute_fluxes_ext_central_structure(domain)
    1188 
     1144#def compute_fluxes(domain):
     1145#    """Compute fluxes and timestep suitable for all volumes in domain.
     1146#
     1147#    Compute total flux for each conserved quantity using "flux_function"
     1148#
     1149#    Fluxes across each edge are scaled by edgelengths and summed up
     1150#    Resulting flux is then scaled by area and stored in
     1151#    explicit_update for each of the three conserved quantities
     1152#    stage, xmomentum and ymomentum
     1153#
     1154#    The maximal allowable speed computed by the flux_function for each volume
     1155#    is converted to a timestep that must not be exceeded. The minimum of
     1156#    those is computed as the next overall timestep.
     1157#
     1158#    Post conditions:
     1159#      domain.explicit_update is reset to computed flux values
     1160#      domain.timestep is set to the largest step satisfying all volumes.
     1161#
     1162#    This wrapper calls the underlying C version of compute fluxes
     1163#    """
     1164#
     1165#    import sys
     1166#    from shallow_water_ext import compute_fluxes_ext_central \
     1167#                                  as compute_fluxes_ext
     1168#
     1169#    # Shortcuts
     1170#    Stage = domain.quantities['stage']
     1171#    Xmom = domain.quantities['xmomentum']
     1172#    Ymom = domain.quantities['ymomentum']
     1173#    Bed = domain.quantities['elevation']
     1174#
     1175#
     1176#
     1177#    timestep = float(sys.maxint)
     1178#
     1179#    flux_timestep = compute_fluxes_ext(timestep,
     1180#                                       domain.epsilon,
     1181#                                       domain.H0,
     1182#                                       domain.g,
     1183#                                       domain.neighbours,
     1184#                                       domain.neighbour_edges,
     1185#                                       domain.normals,
     1186#                                       domain.edgelengths,
     1187#                                       domain.radii,
     1188#                                       domain.areas,
     1189#                                       domain.tri_full_flag,
     1190#                                       Stage.edge_values,
     1191#                                       Xmom.edge_values,
     1192#                                       Ymom.edge_values,
     1193#                                       Bed.edge_values,
     1194#                                       Stage.boundary_values,
     1195#                                       Xmom.boundary_values,
     1196#                                       Ymom.boundary_values,
     1197#                                       Stage.explicit_update,
     1198#                                       Xmom.explicit_update,
     1199#                                       Ymom.explicit_update,
     1200#                                       domain.already_computed_flux,
     1201#                                       domain.max_speed,
     1202#                                       domain.optimise_dry_cells)
     1203#
     1204#    domain.flux_timestep = flux_timestep
     1205#
     1206#
     1207#
     1208#def compute_fluxes_structure(domain):
     1209#    """Compute fluxes and timestep suitable for all volumes in domain.
     1210#
     1211#    Compute total flux for each conserved quantity using "flux_function"
     1212#
     1213#    Fluxes across each edge are scaled by edgelengths and summed up
     1214#    Resulting flux is then scaled by area and stored in
     1215#    explicit_update for each of the three conserved quantities
     1216#    stage, xmomentum and ymomentum
     1217#
     1218#    The maximal allowable speed computed by the flux_function for each volume
     1219#    is converted to a timestep that must not be exceeded. The minimum of
     1220#    those is computed as the next overall timestep.
     1221#
     1222#    Post conditions:
     1223#      domain.explicit_update is reset to computed flux values
     1224#      domain.flux_timestep is set to the largest step satisfying all volumes.
     1225#
     1226#    This wrapper calls the underlying C version of compute fluxes
     1227#    """
     1228#
     1229#
     1230#    from shallow_water_ext import compute_fluxes_ext_central_structure
     1231#
     1232#
     1233#    domain.flux_timestep = compute_fluxes_ext_central_structure(domain)
     1234#
    11891235
    11901236
     
    14011447
    14021448
    1403 def gravity_wb(domain):
    1404     """Apply gravitational pull in the presence of bed slope
    1405     Wrapper calls underlying C implementation
    1406     """
    1407 
    1408     from shallow_water_ext import gravity_wb as gravity_wb_c
    1409 
    1410     gravity_wb_c(domain)
    1411 
    1412 
    1413 def gravity(domain):
    1414     """Apply gravitational pull in the presence of bed slope
    1415     Wrapper calls underlying C implementation
    1416     """
    1417 
    1418     from shallow_water_ext import gravity as gravity_c
    1419 
    1420     gravity_c(domain)
    14211449
    14221450def manning_friction_implicit(domain):
  • trunk/anuga_core/source/anuga/shallow_water/shallow_water_ext.c

    r8380 r8381  
    16011601
    16021602
    1603         printf("h0,1,2 %f %f %f\n",hh[0],hh[1],hh[2]);
     1603        //printf("h0,1,2 %f %f %f\n",hh[0],hh[1],hh[2]);
    16041604       
    16051605        // Calculate the side correction term
     
    16101610            n1 = D.normals[k6+2*i+1];
    16111611
    1612             printf("n0, n1 %i %g %g\n",i,n0,n1);
    1613             fact = 0.5*g*hh[i]*hh[i]*D.edgelengths[k3+i];
     1612            //printf("n0, n1 %i %g %g\n",i,n0,n1);
     1613            fact = -0.5*g*hh[i]*hh[i]*D.edgelengths[k3+i];
    16141614            sidex = sidex + fact*n0;
    16151615            sidey = sidey + fact*n1;
  • trunk/anuga_core/source/anuga/shallow_water/test_shallow_water_domain.py

    r8379 r8381  
    21672167            assert num.allclose(domain.quantities[name].semi_implicit_update, 0)
    21682168
    2169         domain.compute_forcing_terms()
    2170         #from shallow_water_ext import gravity
    2171         #gravity(domain)
     2169        #domain.compute_forcing_terms()
     2170        from shallow_water_ext import gravity
     2171        gravity(domain)
    21722172
    21732173        #print domain.quantities['xmomentum'].explicit_update
     
    21812181
    21822182
    2183 
    2184     def Xtest_gravity_wb(self):
     2183    def test_gravity_2(self):
    21852184        #Assuming no friction
    21862185
     
    22042203            return 3*x
    22052204
    2206         h = 0.1
     2205        h = 15
    22072206        def stage(x, y):
    2208             return slope(x,y)+h
     2207            return h
    22092208
    22102209        domain.set_quantity('elevation', slope)
     
    22152214            assert num.allclose(domain.quantities[name].semi_implicit_update, 0)
    22162215
    2217         from shallow_water_ext import gravity_wb
    2218         gravity_wb(domain)
    2219 
    2220 
    2221         print domain.quantities['xmomentum'].explicit_update
    2222         print domain.quantities['ymomentum'].explicit_update
     2216        #domain.compute_forcing_terms()
     2217        from shallow_water_ext import gravity
     2218        gravity(domain)
     2219
     2220        #print domain.quantities['xmomentum'].explicit_update
     2221        #print domain.quantities['ymomentum'].explicit_update
     2222
     2223
    22232224        assert num.allclose(domain.quantities['stage'].explicit_update, 0)
    22242225        assert num.allclose(domain.quantities['xmomentum'].explicit_update,
    2225                             -g*h*3)
     2226                            [-382.2, -323.4, -205.8, -382.2])
    22262227        assert num.allclose(domain.quantities['ymomentum'].explicit_update, 0)
    22272228
    2228 
    2229     def Xtest_gravity_wb_2(self):
    2230         #Assuming no friction
     2229    def test_gravity_3(self):
     2230        #Showing standard gravity term is not well balanced
    22312231
    22322232        from anuga.config import g
     
    22492249            return 3*x
    22502250
     2251        h = 15
     2252        def stage(x, y):
     2253            return h
     2254
     2255        domain.set_quantity('elevation', slope)
     2256        domain.set_quantity('stage', stage)
     2257
     2258        for name in domain.conserved_quantities:
     2259            assert num.allclose(domain.quantities[name].explicit_update, 0)
     2260            assert num.allclose(domain.quantities[name].semi_implicit_update, 0)
     2261
     2262        domain.set_compute_fluxes_method('original')
     2263        domain.compute_forcing_terms()
     2264
     2265
     2266        print domain.quantities['xmomentum'].explicit_update
     2267        #print domain.quantities['ymomentum'].explicit_update
     2268
     2269
     2270        assert num.allclose(domain.quantities['stage'].explicit_update, 0)
     2271        assert num.allclose(domain.quantities['xmomentum'].explicit_update,
     2272                            [-382.2, -323.4, -205.8, -382.2])
     2273        assert num.allclose(domain.quantities['ymomentum'].explicit_update, 0)
     2274
     2275
     2276    def test_gravity_wb(self):
     2277        #Assuming no friction
     2278
     2279        from anuga.config import g
     2280
     2281        a = [0.0, 0.0]
     2282        b = [0.0, 2.0]
     2283        c = [2.0, 0.0]
     2284        d = [0.0, 4.0]
     2285        e = [2.0, 2.0]
     2286        f = [4.0, 0.0]
     2287
     2288        points = [a, b, c, d, e, f]
     2289        #             bac,     bce,     ecf,     dbe
     2290        vertices = [[1,0,2], [1,2,4], [4,2,5], [3,1,4]]
     2291
     2292        domain = Domain(points, vertices)
     2293
     2294        #Set up for a gradient of (3,0) at mid triangle (bce)
     2295        def slope(x, y):
     2296            return 3*x
     2297
     2298        h = 0.1
     2299        def stage(x, y):
     2300            return slope(x,y)+h
     2301
     2302        domain.set_quantity('elevation', slope)
     2303        domain.set_quantity('stage', stage)
     2304
     2305        for name in domain.conserved_quantities:
     2306            assert num.allclose(domain.quantities[name].explicit_update, 0)
     2307            assert num.allclose(domain.quantities[name].semi_implicit_update, 0)
     2308
     2309        from shallow_water_ext import gravity_wb
     2310        gravity_wb(domain)
     2311
     2312
     2313        #print domain.quantities['xmomentum'].explicit_update
     2314        #print domain.quantities['ymomentum'].explicit_update
     2315
     2316
     2317        assert num.allclose(domain.quantities['stage'].explicit_update, 0)
     2318        assert num.allclose(domain.quantities['xmomentum'].explicit_update,
     2319                            -g*h*3)
     2320        assert num.allclose(domain.quantities['ymomentum'].explicit_update, 0)
     2321
     2322
     2323    def test_gravity_wb_2(self):
     2324        #Assuming no friction
     2325
     2326        from anuga.config import g
     2327
     2328        a = [0.0, 0.0]
     2329        b = [0.0, 2.0]
     2330        c = [2.0, 0.0]
     2331        d = [0.0, 4.0]
     2332        e = [2.0, 2.0]
     2333        f = [4.0, 0.0]
     2334
     2335        points = [a, b, c, d, e, f]
     2336        #             bac,     bce,     ecf,     dbe
     2337        vertices = [[1,0,2], [1,2,4], [4,2,5], [3,1,4]]
     2338
     2339        domain = Domain(points, vertices)
     2340
     2341        #Set up for a gradient of (3,0) at mid triangle (bce)
     2342        def slope(x, y):
     2343            return 3*x
     2344
    22512345        h = 15.0
    22522346        def stage(x, y):
     
    22642358
    22652359
    2266         print domain.quantities['xmomentum'].explicit_update
    2267         print domain.quantities['ymomentum'].explicit_update
     2360        #print domain.quantities['xmomentum'].explicit_update
     2361        #print domain.quantities['ymomentum'].explicit_update
    22682362       
    22692363        assert num.allclose(domain.quantities['stage'].explicit_update, 0)
    22702364        assert num.allclose(domain.quantities['xmomentum'].explicit_update,
    2271                             -g*h*3)
     2365                            [-396.9, -308.7, -220.5, -396.9])
    22722366        assert num.allclose(domain.quantities['ymomentum'].explicit_update, 0)
    22732367
  • trunk/anuga_work/shallow_water_balanced_steve/run_sw_merimbula.py

    r8380 r8381  
    9797#domain.set_CFL(0.7)
    9898#domain.set_beta(1.5)
    99 domain.set_compute_fluxes_method('original')
     99domain.set_compute_fluxes_method('wb_2')
    100100domain.set_name('merimbula')
    101101
Note: See TracChangeset for help on using the changeset viewer.