1

I am trying to calculate the area of six landcover classes within a polygon. However the proportions I get back do not add up to one. For example:

var CL = ee.ImageCollection('USDA/NASS/CDL').select('cropland') //crop data layer for USA
                  .filter(ee.Filter.date('2009-01-01', '2009-12-31')); //example year

var area = ee.Image.pixelArea(); 


// I am reclassifying all images to six basic categories
// 1 - corn
// 2 - cotton
// 3 - soybeans
// 4 - other crop
// 5 - native vegetation (loosely defined)
// 6 - non habitat

var propNames = ee.List(['from', 'to']);
var fromToList = ee.List(
  fromToFc.reduceColumns({
    reducer: ee.Reducer.toList().repeat(propNames.size()),
    selectors: propNames
  })
  .get('list')
);

var from = fromToList.get(0);
var to = fromToList.get(1);

var remapping = function(image) {
  return image.remap(from, to, null, 'cropland');
};

var CL2 = CL.map(remapping);

print('CL2',CL2);




var buffed = geometry.buffer(2500);

var geom_area = buffed.area();
var fcomp = CL2.filterBounds(buffed);
print("fcomp",fcomp)

var fcomp_corn = fcomp.first()
  .mask(fcomp.first().eq(1))
  .multiply(area)
  .divide(geom_area)
  .select([0],['corn']);

var fcomp_cotton = fcomp.first()
  .mask(fcomp.first().eq(2))
  .multiply(area)
  .divide(geom_area)
  .select([0],['cotton']);
  
var fcomp_soy = fcomp.first()
  .mask(fcomp.first().eq(3))
  .multiply(area)
  .divide(geom_area)
  .select([0],['soy']);
  
var fcomp_other = fcomp.first()
  .mask(fcomp.first().eq(4))
  .multiply(area)
  .divide(geom_area)
  .select([0],['other']);
  
var fcomp_native = fcomp.first()
  .mask(fcomp.first().eq(5))
  .multiply(area)
  .divide(geom_area)
  .select([0],['native']);
  
var fcomp_nonhabit = fcomp.first()
  .mask(fcomp.first().eq(6))
  .multiply(area)
  .divide(geom_area)
  .select([0],['nonhabit']);
  


Map.addLayer(fcomp_native.clip(buffed),{},"native");
Map.addLayer(fcomp_nonhabit.clip(buffed),{},"non-habitat");
Map.centerObject(fcomp_nonhabit.clip(buffed));

var area_image = fcomp_corn.addBands(fcomp_cotton)
.addBands(fcomp_soy)
.addBands(fcomp_other)
.addBands(fcomp_native)
.addBands(fcomp_nonhabit);

var areas = area_image.reduceRegion({
reducer:ee.Reducer.sum(),
geometry: buffed,
scale: 30,
maxPixels:1e13
});

print("geometry area",geom_area);

print("areas",areas);

gives me the following proportions

Landcover proportion
corn 0.0278
cotton 0.0000
native 0.6739
nonhabitat 5.1639
other 0.0039
soy 0.0025

Obviously, 'nonhabitat' is wrong here. Does anyone know what is going wrong in my code?

here is the GEE link: https://code.earthengine.google.com/9380d97e4489f43f20787bc79bdc53c2

1 Answer 1

2

I used a simpler approach for calculating areas based in your fcomp image. Code snippet looks as follows and complete code is here.

var fcomp2 = fcomp.first();

var area_image2 = fcomp2
  .rename('area_image2');

//print("area_image2", area_image2);

var mergedAllFunction = function(image) {

 var thres1 = area_image2.eq(1).rename('corn');
 var thres2 = area_image2.eq(2).rename('cotton');
 var thres3 = area_image2.eq(3).rename('soy');
 var thres4 = area_image2.eq(4).rename('other');
 var thres5 = area_image2.eq(5).rename('native');
 var thres6 = area_image2.eq(6).rename('nonhabit');

 return image.addBands(area_image2).addBands([thres1, thres2, thres3, thres4, thres5, thres6]);
};

var median = CL.median();

var merged = mergedAllFunction(median);

//print("merged", merged);

var areas_c = merged
    .select(['corn', 'cotton', 'soy', 'other', 'native', 'nonhabit'])
    .multiply(ee.Image.pixelArea())
    .reduceRegion({
      reducer: ee.Reducer.sum(),
      geometry: buffed,  // a geometry
      scale: 30,   
      maxPixels: 1e9  
    });

print("complete areas in square meters", areas_c); //complete areas in square meters

print("areas sum", ee.List(areas_c.values()).reduce(ee.Reducer.sum()));

var areas_p = merged
    .select(['corn', 'cotton', 'soy', 'other', 'native', 'nonhabit'])
    .multiply(ee.Image.pixelArea().divide(geom_area))
    .reduceRegion({
      reducer: ee.Reducer.sum(),
      geometry: buffed,  // a geometry
      scale: 30,   
      maxPixels: 1e9  
    });

print("areas as proportion", areas_p); //areas as proportion

print("proportion areas sum", ee.List(areas_p.values()).reduce(ee.Reducer.sum()));

After running above code in GEE code editor, I got results of following image. It can be observed that sum areas is comparable with geometry area and the sum of obtained area proportions is 1; as expected (relative errors are very low in both cases).

enter image description here

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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