Urban Flood Risk Model - Serv.built we cannot explain

Hello there,

I am currently running my data sources after pre-processing with Invest’s Urban Flood Risk Mitigation model and am receiving abnormally large service.built values (on the order of E16).

I’ve uploaded a screenshot to the values that I am receiving for R_m3 and Affected build. The calculation to achieve service.built seems correct after manually multiplying those two values, but I can’t seem to explain why the R_m3 is so high.

I created a previous thread on the sample data’s outputs and wanted to clarify two things:

  1. In the documentation it says that this value is in m^3 but I am not sure how that’s gotten if

affected.build is in $ and the sum of R_m3i is in m^3. Could you clarify the units on this output as well as possibly why the resulting value is in the trillions?

  1. How is the spatial resolution being considered in the calculation? I noticed that for R_m3i it is the pixel area * runoff retention per pixel * rainfall depth. I read in a previous thread where the sample data was on a 30m x 30m resolution and for each pixel it had to be multiplied by 900 sqm. Could you clarify how the pixel area is being calculated?

Thanks for the help!


Hi @rxchelzhxng , good questions.

It looks like there could be some misleading things about units in the User’s Guide we should fix. Affected.Build is the product of the sum of building footprints (m^2) * $/m^2 .

So that leaves Service.built with units of m^3 * $

Based on the data you show above, the reason it’s so large has more to do with Affected.Build ($15 billion) - which is mostly driven by the area of building footprint - than the volume of runoff retention (6 million m^3 ).

Pixel area is pixel width * pixel height. And it’s based on the LULC raster input. All other intermediate and final rasters are aligned and resized to your LULC.

So runoff retention volume R \_m^3 = R * P * pixel\_area * 10^-3

where I believe R is unitless, P is millimeters ( 10^-3 converts mm to meters) and pixel_area is m^2

Let me know if this all makes sense to you. I’ll try to make some of this clearer in the User’s Guide.

I originally thought that Affected.Build was the sum of the building footprint area (m^2) multiplied by the potential damage cost in units ($ per m^2). This product would be in dollar units. Could you please confirm the value we input into the Damage.csv table since I am currently inputting a value of dollars per m^2?

As for the service.built, is the meaning of this output the total amount of savings for this watershed given that this is being multiplied by the amount of runoff retained instead of generated? This is only my interpretation of it because I don’t quite understand why the formula is multiplying by the runoff retention and not flood volume. Could you clarify how I should interpret this value?

For the pixel area, does the model consider the spatial resolution (m/pixel)? In our case we are using a land cover of 10m/ pixel resolution and it should differ if one were to use a 30m/ pixel resolution raster? As well as, if the pixel area is pixel width * pixel height does the calculation consider the area surrounding the watershed (the area that’s black) or only the watershed ?

Thanks for the clarification!

Hi @rxchelzhxng ,

You are correct. (If you read my last post immediately when I posted it, there were a couple mistakes I corrected a few minutes later.)

Yes, or another way to describe the valuation is “avoided damages”.

Runoff retention & runoff volume are highly correlated of course, but the “service” provided by the soil/landcover is the service of “retention”. So I think that’s probably why retention is used in the valuation. We’re often trying to answer a question like, “what is the value (avoided damages) provided by the ecosystem service (runoff retention volume)?”

The area of a single pixel is the pixel’s width * height. For your example, 10m * 10m. Each of the variables ( R\_m^3, Q\_m^3 ) that include pixel_area as part of their equation are calculated for each individual pixel. Then for the final summaries of a watershed, those R\_m^3, Q\_m^3 , etc values are summed across all the pixels in the watershed. So those black areas in your image may have values in the output rasters, but only the pixels within the watershed polygons are part of the summaries in the flood_risk_service.shp . I’m not sure if that answered your question. Let me know!

Thanks for clarifying, that makes sense!

Regarding the spatial resolution of 10m/pixel, is that within the metadata of the land cover raster? Or how is the 10m * 10m accounted for in the calculation?

Also, because the current calculation for Affected.build isn’t considering that some buildings will not be affected by the storm, does adding a DEM (digital elevation model) add in that complexity for the calculation? Ideally, we would want to be able to tell which buildings will be affected by this storm that we are simulating.

Thanks once again :slight_smile:

Yes, all raster files store the pixel dimensions in their metadata.

I’m afraid not, this model does not take a DEM input or do any modeling of the flood path. Although it does seem strange that the Affected.build variable is not at all a function of any of the flood variables. So the Affected.build and Service.built would not change under different landuse/soil scenarios. Could that be right? I can try to get some other experts to weigh in on this.

Yes, from what I found Affected.build is not a function of any of the derived runoff retention/potential variables. However, I believe Service.built does include runoff retention volume (m_3).

My team is having some difficulty around the model in terms of wanting it to differentiate which buildings will be exposed to flooding, since not all areas (eg. ones with higher elevation) would be exposed. It’d be great to hear how the experts are interpreting the values and to see if there’s a correlation for the runoff potential (flooding) and economic damage.

Ah right. I was overlooking that Service.built equation. That makes more sense.

I think you may have reached the limits of the model. It’s really meant to compare how different landuse scenarios affect levels of retention. It’s not the best tool for mapping accurate flood extents. Here’s an excerpt from the User’s Guide:

Runoff production: the model uses a simple approach (SCS-Curve Number), which introduces high uncertainties. However, the ranking between different land uses is generally well captured by such an approach, i.e. that the effect of natural infrastructure will be qualitatively represented in the model outputs. Future work will aim to include a routing over the landscape: ideas include TOPMODEL (there is an R package), UFORE (used in iTree), CADDIES, etc

Oh I see, would a possible scenario be if one were to pave over an area and/or include another building footprint and measure the runoff retention difference which would also lead to the amount of damage avoided?

I was also thinking of another approach such that we could overlay another shapefile with high flood prone areas in the watershed. Would you say that the model is capable of evaluating the flood extent with this added shapefile?

Yes, I think that’s a great example of a scenario. Often it’s useful to compare the “biophysical” results of different scenarios - in this case the change in retention amounts. Other times it’s important to compare the “value” of those biophysical services. But it’s always important to understand the limits & assumptions that go into those “value” metrics.

Well whatever you do here would be a post-processing step that you design yourself. There’s nothing programmed in the model to analyze such a shapefile. But it is generally a good idea to think about useful contextual data that might be presented alongside the model results, to better tell the story.


I am currently trying to validate the outputs I am getting for the runoff retention volume and runoff generated volume. It seems to me that the runoff retention volume is a factor of two larger than expected. Based on the quote below,

a manual calculation should give
runoff retention volume R_m3 = 0.51138359305 * (33.8mm) * 226(km_2) * 10^-3 = 3903426.
This is roughly half of what I am getting in the shapefile outputs

Is there possibly a miscalculation that I’ve made or haven’t considered? Any input into interpreting this output would be greatly appreciated!


Hi @rxchelzhxng , the runoff retention values (both index and volume) are calculated per raster pixel. Those equations aren’t meant to work for an entire watershed. The watershed shapefile aggregates raster values, but not in a way that the aggregated values can be plugged back into that same equation. For example, rm_rt_m3 is a sum of the retention volume pixels, but the rm_rt_idx is an average of the retention index pixel values in that watershed. And the P is also still at the scale of a single pixel.

Essentially, your manual calculation estimates runoff retention volume for a single “pixel” with an average R and an area of 226km^2. It doesn’t capture the process of calculating volume on each pixel and then summing them. It’s a little tough to explain, does that make sense?

I see, does that mean this manual calculation no longer applies?

If that is the case, how should I be calculating the volume on each pixel and then summing them? As well as does the model output any intermediate values (sum of building footprint area)?

Thanks a lot!

That’s right, the equation only applies at the pixel scale.

Well that’s exactly what the model does for you! But if you wanted to reproduce the summary step, you would use a “zonal statistics” operation with the watersheds shapefile and the rasters, which are either in the output workspace or in the intermediate_files subfolder. The sum of building footprint area per watershed is not calculated or saved to any of the output files.


Okay that means that equation is used to calculate the runoff retention volume per pixel where R is gotten from the runoff retention index raster?

I am still convinced that there is something missing in either my manual calculation or the output because it doesn’t make sense why the sum of the total runoff retention and runoff generated are not equal to the total rainfall volume. This is my manual calculation:
Volume = width * length * rainfall depth
= 1000 mm x 1000 mm x 33.8 mm
= 33.8E6 mm^3 (0.034 m^3)
= 0.034m^3
Total rainfall volume in watershed = 33400 m^3 per square km * area of watershed (226 km^2) = 7.68E6 m^3

However if I add the sum of runoff retention and sum of runoff generated, I get 7.39E6+7.06E6 =
14E6 m^3
which is 2 times the amount of rainfall volume I’d expect.

I see, in order to calculate the Affected.Build the model calculates the building footprint area. Is this value just not exposed to the user?


That makes sense to me, that rainfall volume should equal runoff vol + retention vol. Your rainfall volume math looks right (except an 8 accidentally changed to a 4?). I get:
0.0338 m * 2.26E8 m^2 = 7,638,799.99 m^3

I guess I would double-check the easiest thing first, which is the area of the watershed. Can you calculate the area in square meters for that polygon you have pictured above?

Or another approach: do this same checking on individual pixels. For example, I just used the sample data with a rainfall depth of 40mm and I get these values for a random pixel that is 30m by 30m in size:

Flood Volume (Q_m3.tif in the intermediate folder): 6.7395 m^3
Flood Retention (runoff_retention_m3.tif): 29.3616 m^3
Rainfall Volume (0.04 meters * 900 m^2) = 36 m^3

(The minor discrepancy here (0.1 m^3) is explained because the pixels are not exactly 30m by 30m, they are actually 30.10477607413818291m by 29.97959155293129641m)

Sort of, but because there are possibly different damage costs for different building types, the model never needs to know the total building footprint of all buildings. It gets the footprint area for each building within a watershed, one at a time, multiples it by the damage cost associated with that building type, and keeps a running sum of the total costs in that watershed. Here’s the relevant code (aoi here refers to watershed polygon) from a function named _calculate_damage_to_infrastructure_in_aoi:

    total_damage = 0.0
    for infrastructure_fid in structures_index.intersection(
        infrastructure_feature = infrastructure_layer.GetFeature(
        infrastructure_geometry = shapely.wkb.loads(
        if aoi_geometry_prep.intersects(infrastructure_geometry):
            intersection_geometry = aoi_geometry_shapely.intersection(
            damage_type = infrastructure_feature.GetField(type_index)
            damage = damage_type_map[damage_type]['damage']
            total_damage += intersection_geometry.area * damage

    aoi_damage[aoi_feature.GetFID()] = total_damage

Yes I’ve tried this and I got roughly the same area as what it reads in QGIS which is 226 km^2.

I tried a manual calculation just checking on the same pixel that is 10 m by 10 m in size and I get:

Flood Volume (Q_m3.tif) = 1.538907 m^3
Flood Retention (runoff_retention_m3.tif) = 4.941521 m^3
Rainfall volume (0.038 meters * 100m^2) = 3.38m^3

In the example you gave they added up to the rainfall volume however mine seems to be two times what I’d expect. I am confused as to why that is.

I see that clarifies a lot, thanks

Hmm that is concerning. No explanations come to mind. If you would like to share your data I’d be happy to take a look.

Sure that would help a lot! Is there an email I can send it to?