Google Earth Engine JavaScript脚本运行需3-5分钟,求优化方案
Google Earth Engine脚本优化方案(保留Landsat与Sentinel日期灵活性)
我的GEE JavaScript脚本逻辑简单,但运行耗时3-5分钟。希望保留Landsat和Sentinel使用不同日期范围的灵活性,求提升运行速度的优化方法。原脚本如下:
// Set geometry of concern var pointJSP = ee.Geometry.Point([86.465263, 20.168076]); // Center the map at that point. Map.centerObject(pointJSP, 14); // Set dates //Sentinel // Time Block 1 var startDate1 = '2024-02-01'; var endDate1 = '2024-03-01'; // Landsat 8 // Time Block 2 var startDate2 = '2024-02-01'; var endDate2 = '2024-03-01'; // Function for calculating and adding indices - NDVI, NDWI, and NDSI - to the image collections var addIndices = function(image) { var ndvi = image.normalizedDifference(['NIR', 'RED']).rename('NDVI'); var ndwi = image.normalizedDifference(['NIR', 'SWIR1']).rename('NDWI'); var ndsi = image.normalizedDifference(['SWIR1', 'SWIR2']).rename('NDSI'); return image.addBands(ndvi).addBands(ndwi).addBands(ndsi); }; // Add permanent water mask // JRC - Occurrence var Water = ee.Image('JRC/GSW1_4/GlobalSurfaceWater').select('occurrence'); var visualization = { bands: ['occurrence'], min: 0.0, max: 100.0, palette: ['ffffff', 'ffbbbb', '0000ff'] }; Map.addLayer(Water, visualization, 'Water Occurrence', false); // Implement a threshold. var permWater = Water.gt(80).unmask(); // Map the threshold. Map.addLayer(permWater, { min: 0, max: 1, palette: ['white', 'blue'] }, 'Water vs Non-water', false); // Visualisation Parameters var visTRUE = { bands: ['RED_p30', 'GREEN_p30', 'BLUE_p30'], min: 8500, max: 14000, gamma: 1.3 }; var visTRUE_sent = { bands: ["RED_p30", "GREEN_p30", "BLUE_p30"], min: 0.0, max: 0.2, gamma: 1.3 } // Define classification image visualization parameters. var classificationVis = { min: 0, max: 2, palette: ['785a5a', 'ffc1b0','d63000' ] // Class 0 = others, class 1 = dry_ponds, class 2 = aquaculture }; // --------------------------------------------------------------------------- // Step 1.2 - Get relevant ImageCollections from Sentinel and Landsat8 // Mask and filter by location, date and cloud-free composite (ref. F4.3), calculate indices, add and rename bands // 2.1 Sentinel var sentinel = sentinelBase.select ( ['B2', 'B3', 'B4', 'B8', 'B11', 'B12'], ['BLUE', 'GREEN', 'RED', 'NIR', 'SWIR1', 'SWIR2'] ); var sentinelIndices = sentinel.map(addIndices); // Composite for Time Block 1 var sentinelImageCol_1 = ee.ImageCollection(sentinelIndices) .filterBounds(SamplingArea) .filterDate(startDate1, endDate1) .filter(ee.Filter.lessThan('CLOUDY_PIXEL_PERCENTAGE', 50)); print('Composite for Sentinel', sentinelImageCol_1); var composite1 = sentinelImageCol_1.reduce(ee.Reducer.percentile([30])).clip(SamplingArea).mask(permWater.eq(0)); Map.addLayer(composite1, visTRUE_sent , 'Composite 1 Sentinel', false); // 2.2 Landsat 8 var landsat8 = landsat8base.select ( ['SR_B2', 'SR_B3', 'SR_B4', 'SR_B5', 'SR_B6', 'SR_B7'], ['BLUE', 'GREEN', 'RED', 'NIR', 'SWIR1', 'SWIR2'] ); var landsat8Indices = landsat8.map(addIndices); // Composite for Time Block 2 var l8ImageCol_2 = ee.ImageCollection(landsat8Indices) .filterBounds(SamplingArea) .filterDate(startDate2, endDate2) .filter(ee.Filter.lessThan('CLOUD_COVER', 50)); print('Composite for Landsat 8', l8ImageCol_2); var composite2 = l8ImageCol_2.reduce(ee.Reducer.percentile([30])).clip(SamplingArea).mask(permWater.eq(0)); Map.addLayer(composite2, visTRUE , 'Composite 2 Landsat', false);
优化建议
- 先过滤再计算指数:当前脚本先给整个影像集添加指数,再做空间、时间、云量过滤,会浪费算力处理大量无关图像。调整顺序:先对
sentinelBase/landsat8base做filterBounds、filterDate、云量过滤,再执行select和map(addIndices)。比如Sentinel部分修改为:var sentinelImageCol_1 = sentinelBase .filterBounds(SamplingArea) .filterDate(startDate1, endDate1) .filter(ee.Filter.lessThan('CLOUDY_PIXEL_PERCENTAGE', 50)) .select(['B2', 'B3', 'B4', 'B8', 'B11', 'B12'], ['BLUE', 'GREEN', 'RED', 'NIR', 'SWIR1', 'SWIR2']) .map(addIndices); - 移除不必要的调试输出:
print语句会触发影像集的计算,调试完成后建议注释掉,减少额外计算开销。 - 利用QA波段精准过滤云:仅靠
CLOUDY_PIXEL_PERCENTAGE或CLOUD_COVER字段过滤不够精准,建议结合影像的QA波段(比如Sentinel-2的QA60、Landsat 8的QA_PIXEL)做像素级云掩膜,减少无效像素参与合成,提升计算效率。 - 优化掩码范围:
permWater可以提前裁剪到SamplingArea范围,减少掩码数据的处理量:var permWater = Water.gt(80).unmask().clip(SamplingArea); - 减少冗余波段计算:如果后续分析不需要所有指数(NDVI/NDWI/NDSI)的百分位数,在合成前筛选出需要的波段,避免计算无用数据。
内容的提问来源于stack exchange,提问作者Garima Jain
相关产品推荐
相关产品推荐

