2

Objective:
I work with an image collection and have calculated a mean value derived from the ee.Reducer.mean function. I would like get this mean value exported together with band pixel values when i sample the collection.

Background
I have managed to get the reducer mean output stored as a property using image.set, but i repeatedly run into problems when I try to access it using the get function (I have some ideas of why, but I do not want to clutter this question too much).

My attempted solution
Instead I was thinking of adding my mean value as a constant value band and sample it in the same fashion as the other bands.

I have thought about two reasonable candidates for this task (I am currently running for number 2): 1) Getting the value from the property in a similar manner to this example. (The central command reads as follow: img=img.addBands(ee.Image.constant(img.get('system:time_start')).rename('time'));).
But I am unable to successfully access the value using the get function.

1) Apply the value as a new band directly after applying the reducer function. The code below show's my unsuccessful attempt with this method, resulting in a Parameter 'value' is required error.

// Define study area
var studya_area_geometry = 
    ee.Geometry.Polygon(
        [[[-4.861076352175587, 14.291647050733893],
          [-4.861076352175587, 14.235081371627722],
          [-4.788463589724415, 14.235081371627722],
          [-4.788463589724415, 14.291647050733893]]], null, false);

// Add collection          
var study_site_collection = ee.ImageCollection('LANDSAT/LC08/C01/T1_SR')
    .filterDate('2018-01-01', '2018-02-17') // Filter dates
  .filterBounds(studya_area_geometry); // Filter bounding box


// Define function to use Reducer.mean specifically on band 2 ('B2') in collection.
var mean_function_selected_band = function(image) { 
  var B2_band = image.select('B2');
    var B2_band_mean = B2_band.reduceRegion({
      reducer: ee.Reducer.mean(),
      geometry: studya_area_geometry,
      scale: 30
    });

    return(image.addBands(ee.Image.constant(B2_band_mean).rename('B2_mean')));

    // I have tried to cast the value using following command, but it does not work either
  // return(image.addBands(ee.Image.constant(ee.Number.parse(B2_band_mean)).rename('B2_mean')));

  // The alternative solution mentioned above would be to save the value
  // as a property instead using following command, but I have not been able to solve it any how:
     // return(image.set('B2_mean',B2_band_mean));

};  

// Apply function
var collection_containing_mean = study_site_collection.map(mean_function_selected_band);
print(collection_containing_mean);

My thoughts
I assume that the error message indicates that reducer output is not stored in a numerical format that server understands. I have tried to print it to see how the output is structured, but just get another error, leaving me in the dark to figure out how to cast or the transform the value.

Stack Exchange has been very useful to gather clues on what might be wrong in my code, but I haven't been able to wrap my head around all the possibilities.

4

reducer output is not stored in a numerical format that server understands

Sort of. Remember, image.select('B2') does not give you a band; it gives you an image which has only one band. Operations on images always work as if there might be multiple bands.

Therefore, the value you called B2_band_mean is not a number: it is a Dictionary of band names and numbers, like {'B2': 766.0760687834286}. So, you need to fetch the element 'B2' out of that dictionary.

This modification to your code will put a property with the mean as a number on each image:

var mean_function_selected_band = function(image) { 
  var B2_band = image.select('B2');
  var B2_band_mean = B2_band.reduceRegion({
    reducer: ee.Reducer.mean(),
    geometry: studya_area_geometry,
    scale: 30
  }).get('B2');    // added get() call
  return image.set('B2_mean',B2_band_mean);
};
  • Thank you for a very clear and informative answer. It confirms what I suspected (I had noticed that the value was stored as a sub division of the dictionary, but I had no idea of how to deal with it). – Smerla Dec 9 '19 at 9:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.