卫星嵌入可用于标准遥感分类工作流。这些嵌入专门设计用于在少样本学习方面表现出色,这意味着只需相对较少的已标记数据(例如数十到数百个样本)即可实现高质量的分类结果。由于嵌入包含光谱、空间和时间背景信息,因此简单的分类器(例如 k-Nearest Neighbors (kNN) 或 Random Forest)可以使用嵌入向量将复杂的景观分类为目标类别。
在本教程中,我们将学习如何使用 kNN 分类器通过卫星嵌入来对红树林进行分类,从而采用监督式学习方法。
选择区域
我们先来定义一个感兴趣的区域。在本教程中,我们将选择肯尼亚海岸线沿线的一个区域,并将一个多边形定义为几何变量。或者,您也可以使用代码编辑器中的绘图工具在感兴趣的区域周围绘制一个多边形,该多边形将作为几何图形变量保存在“导入”中。
var geometry = ee.Geometry.Polygon([[
[39.4926, -4.39833],
[39.4926, -4.47394],
[39.5491, -4.47394],
[39.5491, -4.39833]
]])
图:选择红树林分类的感兴趣区域
收集训练样本
使用卫星嵌入的分类工作流只需少量带标签的样本即可获得相对准确的结果。对于地表覆盖分类,最简单的方法是在 Earth Engine 中放置点并为其添加标签,以创建训练样本。我们将创建一个 3 类分类,用于将卫星嵌入中的每个像素分类为以下三个类别之一:
土地覆盖类别 | 说明 | 类别值 |
---|---|---|
红树林 | 所有耐盐的沿海植被物种 | 1 |
水 | 所有地表水 - 湖泊、池塘、河流、海洋等 | 2 |
其他 | 所有其他地表 - 包括建筑、裸露的土壤、沙地、农作物、树木等 | 3 |
为了能够正确标记点,我们首先创建一个 Sentinel-2 无云合成影像并加载它。我们选择了一种假彩色可视化效果,可突出显示水、植被和建筑表面之间的差异,以便我们轻松选择合适的样本。
// Pick a year for classification
var year = 2020;
var startDate = ee.Date.fromYMD(year, 1, 1);
var endDate = startDate.advance(1, 'year');
// Create a Sentinel-2 composite for the selected year
// for selecting training samples
var s2 = ee.ImageCollection('COPERNICUS/S2_SR_HARMONIZED');
var filteredS2 = s2
.filter(ee.Filter.date(startDate, endDate))
.filter(ee.Filter.bounds(geometry));
// Use the Cloud Score+ collection for cloud masking
var csPlus = ee.ImageCollection('GOOGLE/CLOUD_SCORE_PLUS/V1/S2_HARMONIZED');
var csPlusBands = csPlus.first().bandNames();
var filteredS2WithCs = filteredS2.linkCollection(csPlus, csPlusBands);
function maskLowQA(image) {
var qaBand = 'cs';
var clearThreshold = 0.6;
var mask = image.select(qaBand).gte(clearThreshold);
return image.updateMask(mask);
}
var filteredS2Masked = filteredS2WithCs
.map(maskLowQA)
.select('B.*');
// Create a median composite of cloud-masked images
var composite = filteredS2Masked.median();
// Display the input composite
var swirVis = {min: 300, max: 4000, bands: ['B11', 'B8', 'B4']};
Map.centerObject(geometry);
Map.addLayer(composite.clip(geometry), swirVis, 'S2 Composite (False Color)');
图:Sentinel-2 假彩色合成图
现在,我们有了一个目标年份的参考图片,可用于标记样本以进行分类。首先,我们将配置用于收集样本的层。打开几何图形导入部分,然后点击 + 新图层。
图:创建新层
点击新图层旁边的“修改图层属性”(齿轮图标),然后按如下所示进行配置。输入 mangroves
作为图层名称,并将类型更改为 FeatureCollection
。点击 + 属性,然后添加一个值为 1
的新属性 landcover
。将颜色更改为某种绿色阴影,然后点击“确定”。
图:配置红树林图层的图层属性
同样,为其他类别添加 2 个新层。使用 landcover
值,其中 2
表示水,3
表示其他。
图:配置(左)水层和(右)其他图层的图层属性
配置好图层后,我们就可以开始收集样本了。放大到某个区域,直观地识别不同类别的像素。选择 mangroves
图层,然后使用添加标记工具在属于红树林(在我们的假彩色 Sentinel-2 复合影像中通常呈现为中等色调的绿色)的像素上放置点(您还可以查看卫星底图视图以供参考)。使用卫星嵌入数据集进行分类时,您不需要很多点;更重要的是选择能够代表感兴趣区域内变异性的优质示例。在本教程中,一组 10 个样本应该就足够了。
图:收集红树林类别的样本
接下来,切换到 water
图层,并收集地表水像素的样本。由于开放水域对 SWIR 波段的吸收很强,因此在 Sentinel-2 复合影像中,地表水像素几乎呈现黑色。针对 other
层重复此流程,选择明显既不是 mangrove
也不是 water
的示例。
图:收集水和其他类别的样本
训练样本收集现已完成。我们可以将这三个单独的 FeatureCollection 合并为单个地面控制点 (gcp) 集合。
var gcps = mangroves.merge(water).merge(other);
训练分类器
现在,我们准备好训练分类器了。我们加载卫星嵌入数据集,过滤出所选年份和感兴趣区域的图块,创建镶嵌图,然后对嵌入向量进行抽样以创建训练数据集。
var embeddings = ee.ImageCollection('GOOGLE/SATELLITE_EMBEDDING/V1/ANNUAL');
var embeddingsFiltered = embeddings
.filter(ee.Filter.date(startDate, endDate))
.filter(ee.Filter.bounds(geometry));
var embeddingsImage = embeddingsFiltered.mosaic();
// Overlay the samples on the image to get training data.
var training = embeddingsImage.sampleRegions({
collection: gcps,
properties: ['landcover'],
scale: 10
});
print('Training Feature', training.first());
训练特征将嵌入向量作为输入属性,并将关联的标签作为类属性。现在,我们可以使用这些提取的特征来训练分类器。我们可以从 Earth Engine 中提供的各种分类器中进行选择。对于少样本分类(使用极少量样本进行分类,如我们的示例),k-最近邻 (kNN) 是一个不错的选择。在 kNN 分类中,带标签的示例用于“划分”或聚类嵌入空间,并根据嵌入空间中最邻近的邻居的标签为每个像素分配标签。我们来使用训练数据训练 kNN 分类器。
var classifier = ee.Classifier.smileKNN().train({
features: training,
classProperty: 'landcover',
inputProperties: embeddingsImage.bandNames()
});
对 Satellite Embedding 马赛克进行分类
现在,我们可以使用训练好的分类器来预测卫星嵌入马赛克中所有像素的类别。
var classified = embeddingsImage.classify(classifier);
将分类后的图片导出到素材资源(可选)
如果您尝试对大区域进行分类,Earth Engine 需要的时间会超出交互式计算环境允许的时间。最好将中间结果导出为资源,以利用批处理计算环境,该环境的任务执行时间限制更长,资源也更多。这也有助于在处理大型区域时克服计算超时或用户内存超出错误。我们来导出分类后的图片。
// Replace this with your asset folder
// The folder must exist before exporting
var exportFolder = 'projects/spatialthoughts/assets/satellite_embedding/';
var classifiedExportImage = 'mangrove_classification';
var classifiedExportImagePath = exportFolder + classifiedExportImage;
Export.image.toAsset({
image: classified.clip(geometry),
description: 'Classified_Image_Export',
assetId: classifiedExportImagePath,
region: geometry,
scale: 10,
maxPixels: 1e10
});
启动导出任务,并等待其完成,然后再继续操作。导出任务完成后,我们将分类后的图片重新导入到代码中。
// Use the exported asset
var classified = ee.Image(classifiedExportImagePath);
直观呈现分类
无论您是以交互方式运行分类,还是导出到资源,现在您都将获得一个包含分类结果的分类变量。
// Choose a 3-color palette
// Assign a color for each class in the following order
// Mangrove, Water, Other
var palette = ['green', 'blue', 'gray'];
Map.addLayer(
classified.clip(geometry),
{min: 1, max: 3, palette: palette},
'Classified Satellite Embeddings Image');
图:分类的卫星嵌入图像
创建红树林地图
我们创建了一个包含 3 个类别的分类图片。我们可以提取分类为红树林(类别 1)的像素,以创建红树林地图。
// Extract mangroves class
var mangrovesImage = classified.eq(1).selfMask();
var mangroveVis = {min: 0, max: 1, palette: ['green']};
Map.addLayer(mangrovesImage.clip(geometry),
mangroveVis, 'Mangroves Map (Satellite Embedding Classification)');
图:红树林地图
验证结果
为了评估我们的结果,我们可以将其与高质量的同行评审数据集(即 Global Mangrove Watch)进行比较。此数据集源自 JAXA 的 L 波段合成孔径雷达 (SAR),包含 1996 年至 2020 年的年度红树林地图。此数据集可在 GEE 社区目录中找到,因此我们可以轻松地在 Earth Engine 中加载和直观呈现它。
var gmw = ee.ImageCollection(
'projects/earthengine-legacy/assets/projects/sat-io/open-datasets/GMW/extent/GMW_V3');
var gmwFiltered = gmw
.filter(ee.Filter.date(startDate, endDate))
.filter(ee.Filter.bounds(geometry));
var gmwImage = gmwFiltered.first();
Map.addLayer(gmwImage.clip(geometry),
mangroveVis, 'Mangroves (Global Mangrove Watch)');
请注意,全球红树林观测结果与卫星嵌入数据集的少样本分类输出结果非常接近。如果您将底图切换为“卫星”,您会发现“卫星嵌入”分类还捕获了全球红树林观测分类中缺失的更精细的景观细节。