卷积

如需对图片执行线性卷积,请使用 image.convolve()。卷积的唯一参数是 ee.Kernel,它由形状和核中的权重指定。convolve() 输出的图片的每个像素都是核值和核所覆盖的输入图片像素的线性组合。这些核会分别应用于每个波段。例如,您可能需要使用低通(平滑)核来移除高频信息。下图展示了应用于 Landsat 8 图像的 15x15 低通滤波核:

Code Editor (JavaScript)

// Load and display an image.
var image = ee.Image('LANDSAT/LC08/C02/T1_TOA/LC08_044034_20140318');
Map.setCenter(-121.9785, 37.8694, 11);
Map.addLayer(image, {bands: ['B5', 'B4', 'B3'], max: 0.5}, 'input image');

// Define a boxcar or low-pass kernel.
var boxcar = ee.Kernel.square({
  radius: 7, units: 'pixels', normalize: true
});

// Smooth the image by convolving with the boxcar kernel.
var smooth = image.convolve(boxcar);
Map.addLayer(smooth, {bands: ['B5', 'B4', 'B3'], max: 0.5}, 'smoothed');

使用低通滤波进行卷积的输出应如下图 1 所示。请注意,内核的参数决定了其大小和系数。 具体而言,如果将 units 参数设置为像素,则 radius 参数会指定内核将从中心覆盖的像素数。如果将 normalize 设置为 true,则核函数系数的总和为 1。如果设置了 magnitude 参数,则核函数系数将乘以幅度(如果 normalize 也为 true,则系数的总和为 magnitude)。如果任何核函数系数中都包含负值,将 normalize 设为 true 会使系数的总和为零。

boxcar_sf
图 1. 与平滑核卷积的 Landsat 8 图像。 美国加利福尼亚州旧金山湾区。

使用其他内核来实现所需的图像处理效果。此示例使用拉普拉斯核进行各向同性边缘检测:

Code Editor (JavaScript)

// Define a Laplacian, or edge-detection kernel.
var laplacian = ee.Kernel.laplacian8({ normalize: false });

// Apply the edge-detection kernel.
var edgy = image.convolve(laplacian);
Map.addLayer(edgy,
             {bands: ['B5', 'B4', 'B3'], max: 0.5, format: 'png'},
             'edges');

请注意可视化参数中的格式说明符。为了提高效率,Earth Engine 会以 JPEG 格式将显示图块发送到代码编辑器,但边缘图块会以 PNG 格式发送,以处理图片边界外的像素透明度。如果出现视觉断点,将格式设置为 PNG 会导致显示不一致。与拉普拉斯边缘检测核卷积的结果应如图 2 所示。

laplacian_sf
图 2. 与拉普拉斯边缘检测核卷积的 Landsat 8 图像。 美国加利福尼亚州旧金山湾区。

此外,还有各向异性边缘检测核(例如 Sobel、Prewitt、Roberts),其方向可以使用 kernel.rotate() 更改。其他低通滤波核包括高斯核和具有均匀权重的各种形状的核。如需创建具有任意定义的权重和形状的核,请使用 ee.Kernel.fixed()。例如,以下代码会创建一个 9x9 的核,其中包含一个位于中间的零:

Code Editor (JavaScript)

// Create a list of weights for a 9x9 kernel.
var row = [1, 1, 1, 1, 1, 1, 1, 1, 1];
// The center of the kernel is zero.
var centerRow = [1, 1, 1, 1, 0, 1, 1, 1, 1];
// Assemble a list of lists: the 9x9 kernel weights as a 2-D matrix.
var rows = [row, row, row, row, centerRow, row, row, row, row];
// Create the kernel from the weights.
var kernel = ee.Kernel.fixed(9, 9, rows, -4, -4, false);
print(kernel);