I'm getting this error when trying to map the result after calculating the seasonal median NDVI images for a time series with 7 different landsat tiles in Google Earth Engine:
Link to the code : https://code.earthengine.google.com/5ec4decebe224dcb8de73ed8c632c55f
Here is the code I'm using (sorry for the missing semi-colons):
var AOI_ZIM = ee.Geometry.Polygon(
[[[25.02396766047741,-17.741728052677256],
[26.56205359797741,-20.059388167694156],
[28.28690711360241,-20.22441903223353],
[28.42972937922741,-18.149348821775746],
[25.02396766047741,-17.741728052677256]
]])
//Image Collection//
var surfaceReflectanceL5 = ee.ImageCollection('LANDSAT/LT05/C01/T1_SR').select(['B3', 'B4', 'pixel_qa'])
.filterDate('1990-01-01', '2002-12-31')
.filterBounds(AOI_ZIM)
var surfaceReflectanceL7 = ee.ImageCollection('LANDSAT/LE07/C01/T1_SR').select(['B3', 'B4', 'pixel_qa'])
.filterDate('1990-01-01', '2002-12-31')
.filterBounds(AOI_ZIM)
var combined_L5L7 = surfaceReflectanceL5.merge(surfaceReflectanceL7)
var filtered_L5L7 = combined_L5L7.filter(ee.Filter.or(ee.Filter.and(ee.Filter.eq('WRS_PATH', 173), ee.Filter.eq('WRS_ROW', 74)), ee.Filter.and(ee.Filter.eq('WRS_PATH', 174), ee.Filter.eq('WRS_ROW', 72))).not())
//Mask clouds and shadows with the QA band//
var cloudMask_L5L7 = function(image) {
var qa = image.select('pixel_qa')
var R_NIR = image.select(['B3', 'B4'])
var qa_thresholds = qa.bitwiseAnd(1 << 5)
.and(qa.bitwiseAnd(1 << 6))
.or(qa.bitwiseAnd(1 << 3))
return R_NIR.updateMask(qa_thresholds.not())
}
var masked_L5L7 = filtered_L5L7.map(cloudMask_L5L7)
//Compute NDVI collection//
var calculateNDVI = function(scene) {
var dateString = ee.Date(scene.get('system:time_start')).format('yyyyMMdd').cat('_').cat(ee.String(ee.Number(scene.get('WRS_PATH')).int())).cat(ee.String(ee.Number(scene.get('WRS_ROW')).int())).cat('_ndvi')
var NDVI_band = scene.normalizedDifference(['B4', 'B3']).multiply(10000).int16()
var add_band = scene.addBands(NDVI_band)
return add_band.select('nd').rename(dateString)
}
var NDVIcollection = masked_L5L7.map(calculateNDVI)
//Calculate the median NDVI per season//
var years = ee.List.sequence(1990, 2002) //years
var list_path = ee.List.sequence(171, 173) //tile path ID
var list_row = ee.List.sequence(72, 74) //tile row ID
var stackList = function(collection) {
var first = ee.Image(collection.get(0)).select([])
var appendBands = function(image, previous) {
return ee.Image(previous).addBands(image)
}
return ee.Image(collection.iterate(appendBands, first))
}
//Calculate median images
var median_NDVI = ee.ImageCollection.fromImages(years.map(function(y) {
//filter by season
var inSeason = NDVIcollection.filter(ee.Filter.calendarRange(y,y,'year')).filter(ee.Filter.calendarRange(10,4,'month'))
var offSeason = NDVIcollection.filter(ee.Filter.calendarRange(y,y,'year')).filter(ee.Filter.calendarRange(5,9,'month'))
//filter the in-season images by tile
var path_list_in = function(path) {
var filter_row_in = list_row.map(function(row) {
var filter_tile_in = inSeason.filter(ee.Filter.and(ee.Filter.eq('WRS_PATH', path),ee.Filter.eq('WRS_ROW', row)))
var inSeason_string = ee.String(ee.Number(y).int()).cat('_').cat(ee.String(ee.Number(path).int())).cat(ee.String(ee.Number(row).int())).cat('_inSeason')
return filter_tile_in.median().rename(inSeason_string)
})
return filter_row_in
}
var medians_inSeason = list_path.map(path_list_in).flatten()
var stack_inSeason = stackList(medians_inSeason)
//filter the off-season images by tile
var path_list_off = function(path) {
var filter_row_off = list_row.map(function(row) {
var filter_tile_off = offSeason.filter(ee.Filter.and(ee.Filter.eq('WRS_PATH', path),ee.Filter.eq('WRS_ROW', row)))
var offSeason_string = ee.String(ee.Number(y).int()).cat('_').cat(ee.String(ee.Number(path).int())).cat(ee.String(ee.Number(row).int())).cat('_offSeason')
return filter_tile_off.median().rename(offSeason_string)
})
return filter_row_off
}
var medians_offSeason = list_path.map(path_list_off).flatten()
var stack_offSeason = stackList(medians_offSeason)
return stack_inSeason.addBands(stack_offSeason).int16()
})) //returns an image collection with 13 images (elements), one per year, with 14 bands (1 band per season (x2) and per tile (x7))
var listMedians_coll = median_NDVI.toList(median_NDVI.size())
var Median_image = ee.Image(listMedians_coll.get(0))
Map.addLayer(Median_image, {bands: '1990_17173_inSeason', min:0, max:10000}, "Median")
Data types are consistent between all bands in the new image collection median_NDVI
(signed int16) and between the original NDVIcollection
and the new image collection, so I guess the problem must come from the fact that median_NDVI
collection images have bands corresponding to different tiles, and therefore not spatially consistent.
What is the proper way to calculate these images?