Объявление : Все некоммерческие проекты, зарегистрированные для использования Earth Engine до
15 апреля 2025 года, должны
подтвердить некоммерческое право на сохранение доступа к Earth Engine.
Преобразования массива
Оптимизируйте свои подборки
Сохраняйте и классифицируйте контент в соответствии со своими настройками.
Earth Engine поддерживает преобразования массивов, такие как транспонирование, инверсия и псевдоинверсия. В качестве примера рассмотрим обычную регрессию временных рядов изображений по методу наименьших квадратов (OLS). В следующем примере изображение с полосами для предикторов и ответом преобразуется в изображение массива, затем «решается» для получения оценок коэффициентов наименьших квадратов тремя способами. Сначала соберите данные изображения и преобразуйте их в массивы:
Редактор кода (JavaScript)
// Scales and masks Landsat 8 surface reflectance images.
function prepSrL8(image) {
// Develop masks for unwanted pixels (fill, cloud, cloud shadow).
var qaMask = image.select('QA_PIXEL').bitwiseAnd(parseInt('11111', 2)).eq(0);
var saturationMask = image.select('QA_RADSAT').eq(0);
// Apply the scaling factors to the appropriate bands.
var opticalBands = image.select('SR_B.').multiply(0.0000275).add(-0.2);
var thermalBands = image.select('ST_B.*').multiply(0.00341802).add(149.0);
// Replace the original bands with the scaled ones and apply the masks.
return image.addBands(opticalBands, null, true)
.addBands(thermalBands, null, true)
.updateMask(qaMask)
.updateMask(saturationMask);
}
// Load a Landsat 8 surface reflectance image collection.
var collection = ee.ImageCollection('LANDSAT/LC08/C02/T1_L2')
// Filter to get only two years of data.
.filterDate('2019-04-01', '2021-04-01')
// Filter to get only imagery at a point of interest.
.filterBounds(ee.Geometry.Point(-122.08709, 36.9732))
// Prepare images by mapping the prepSrL8 function over the collection.
.map(prepSrL8)
// Select NIR and red bands only.
.select(['SR_B5', 'SR_B4'])
// Sort the collection in chronological order.
.sort('system:time_start', true);
// This function computes the predictors and the response from the input.
var makeVariables = function(image) {
// Compute time of the image in fractional years relative to the Epoch.
var year = ee.Image(image.date().difference(ee.Date('1970-01-01'), 'year'));
// Compute the season in radians, one cycle per year.
var season = year.multiply(2 * Math.PI);
// Return an image of the predictors followed by the response.
return image.select()
.addBands(ee.Image(1)) // 0. constant
.addBands(year.rename('t')) // 1. linear trend
.addBands(season.sin().rename('sin')) // 2. seasonal
.addBands(season.cos().rename('cos')) // 3. seasonal
.addBands(image.normalizedDifference().rename('NDVI')) // 4. response
.toFloat();
};
// Define the axes of variation in the collection array.
var imageAxis = 0;
var bandAxis = 1;
// Convert the collection to an array.
var array = collection.map(makeVariables).toArray();
// Check the length of the image axis (number of images).
var arrayLength = array.arrayLength(imageAxis);
// Update the mask to ensure that the number of images is greater than or
// equal to the number of predictors (the linear model is solvable).
array = array.updateMask(arrayLength.gt(4));
// Get slices of the array according to positions along the band axis.
var predictors = array.arraySlice(bandAxis, 0, 4);
var response = array.arraySlice(bandAxis, 4);
Настройка Python
См. страницу «Среда Python» для получения информации об API Python и использовании geemap
для интерактивной разработки.
import ee
import geemap.core as geemap
Колаб (Питон)
import math
# Scales and masks Landsat 8 surface reflectance images.
def prep_sr_l8(image):
# Develop masks for unwanted pixels (fill, cloud, cloud shadow).
qa_mask = image.select('QA_PIXEL').bitwiseAnd(int('11111', 2)).eq(0)
saturation_mask = image.select('QA_RADSAT').eq(0)
# Apply the scaling factors to the appropriate bands.
optical_bands = image.select('SR_B.').multiply(0.0000275).add(-0.2)
thermal_bands = image.select('ST_B.*').multiply(0.00341802).add(149.0)
# Replace the original bands with the scaled ones and apply the masks.
return (
image.addBands(optical_bands, None, True)
.addBands(thermal_bands, None, True)
.updateMask(qa_mask)
.updateMask(saturation_mask)
)
# Load a Landsat 8 surface reflectance image collection.
collection = (
ee.ImageCollection('LANDSAT/LC08/C02/T1_L2')
# Filter to get only two years of data.
.filterDate('2019-04-01', '2021-04-01')
# Filter to get only imagery at a point of interest.
.filterBounds(ee.Geometry.Point(-122.08709, 36.9732))
# Prepare images by mapping the prep_sr_l8 function over the collection.
.map(prep_sr_l8)
# Select NIR and red bands only.
.select(['SR_B5', 'SR_B4'])
# Sort the collection in chronological order.
.sort('system:time_start', True)
)
# This function computes the predictors and the response from the input.
def make_variables(image):
# Compute time of the image in fractional years relative to the Epoch.
year = ee.Image(image.date().difference(ee.Date('1970-01-01'), 'year'))
# Compute the season in radians, one cycle per year.
season = year.multiply(2 * math.pi)
# Return an image of the predictors followed by the response.
return (
image.select()
.addBands(ee.Image(1)) # 0. constant
.addBands(year.rename('t')) # 1. linear trend
.addBands(season.sin().rename('sin')) # 2. seasonal
.addBands(season.cos().rename('cos')) # 3. seasonal
.addBands(image.normalizedDifference().rename('NDVI')) # 4. response
.toFloat()
)
# Define the axes of variation in the collection array.
image_axis = 0
band_axis = 1
# Convert the collection to an array.
array = collection.map(make_variables).toArray()
# Check the length of the image axis (number of images).
array_length = array.arrayLength(image_axis)
# Update the mask to ensure that the number of images is greater than or
# equal to the number of predictors (the linear model is solvable).
array = array.updateMask(array_length.gt(4))
# Get slices of the array according to positions along the band axis.
predictors = array.arraySlice(band_axis, 0, 4)
response = array.arraySlice(band_axis, 4)
Обратите внимание, что arraySlice()
возвращает все изображения во временном ряду для диапазона индексов, указанного вдоль bandAxis
(ось 1). На этом этапе матричную алгебру можно использовать для определения коэффициентов МНК:
Редактор кода (JavaScript)
// Compute coefficients the hard way.
var coefficients1 = predictors.arrayTranspose().matrixMultiply(predictors)
.matrixInverse().matrixMultiply(predictors.arrayTranspose())
.matrixMultiply(response);
Настройка Python
См. страницу «Среда Python» для получения информации об API Python и использовании geemap
для интерактивной разработки.
import ee
import geemap.core as geemap
Колаб (Питон)
# Compute coefficients the hard way.
coefficients_1 = (
predictors.arrayTranspose()
.matrixMultiply(predictors)
.matrixInverse()
.matrixMultiply(predictors.arrayTranspose())
.matrixMultiply(response)
)
Хотя этот метод работает, он неэффективен и затрудняет чтение кода. Лучший способ — использовать метод pseudoInverse()
( matrixPseudoInverse()
для изображения массива):
Редактор кода (JavaScript)
// Compute coefficients the easy way.
var coefficients2 = predictors.matrixPseudoInverse()
.matrixMultiply(response);
Настройка Python
См. страницу «Среда Python» для получения информации об API Python и использовании geemap
для интерактивной разработки.
import ee
import geemap.core as geemap
Колаб (Питон)
# Compute coefficients the easy way.
coefficients_2 = predictors.matrixPseudoInverse().matrixMultiply(response)
С точки зрения читаемости и эффективности вычислений лучший способ получить коэффициенты МНК — это solve()
( matrixSolve()
для изображения массива). solve()
определяет, как лучше всего решить систему, исходя из характеристик входных данных, используя псевдообратное для переопределенных систем, обратное для квадратных матриц и специальные методы для почти сингулярных матриц:
Редактор кода (JavaScript)
// Compute coefficients the easiest way.
var coefficients3 = predictors.matrixSolve(response);
Настройка Python
См. страницу «Среда Python» для получения информации об API Python и использовании geemap
для интерактивной разработки.
import ee
import geemap.core as geemap
Колаб (Питон)
# Compute coefficients the easiest way.
coefficients_3 = predictors.matrixSolve(response)
Чтобы получить многоканальное изображение, спроецируйте изображение массива в пространство меньшей размерности, а затем сгладьте его:
Редактор кода (JavaScript)
// Turn the results into a multi-band image.
var coefficientsImage = coefficients3
// Get rid of the extra dimensions.
.arrayProject([0])
.arrayFlatten([
['constant', 'trend', 'sin', 'cos']
]);
Настройка Python
См. страницу «Среда Python» для получения информации об API Python и использовании geemap
для интерактивной разработки.
import ee
import geemap.core as geemap
Колаб (Питон)
# Turn the results into a multi-band image.
coefficients_image = (
coefficients_3
# Get rid of the extra dimensions.
.arrayProject([0]).arrayFlatten([['constant', 'trend', 'sin', 'cos']])
)
Изучите результаты трех методов и обратите внимание, что результирующая матрица коэффициентов одинакова независимо от решателя. Гибкость и эффективность solve()
делает его хорошим выбором для линейного моделирования общего назначения.
Если не указано иное, контент на этой странице предоставляется по лицензии Creative Commons "С указанием авторства 4.0", а примеры кода – по лицензии Apache 2.0. Подробнее об этом написано в правилах сайта. Java – это зарегистрированный товарный знак корпорации Oracle и ее аффилированных лиц.
Последнее обновление: 2025-07-24 UTC.
[null,null,["Последнее обновление: 2025-07-24 UTC."],[[["\u003cp\u003eEarth Engine enables array transformations like transpose, inverse, and pseudo-inverse for advanced analysis, such as ordinary least squares (OLS) regression on image time series.\u003c/p\u003e\n"],["\u003cp\u003eUsers can convert image collections to arrays, extract predictors and responses, and apply matrix operations to derive regression coefficients.\u003c/p\u003e\n"],["\u003cp\u003eEarth Engine offers multiple methods for solving linear systems, with \u003ccode\u003esolve()\u003c/code\u003e being the most efficient and adaptable for various scenarios, including overdetermined systems and nearly singular matrices.\u003c/p\u003e\n"],["\u003cp\u003eArray images resulting from calculations can be transformed back into multi-band images for visualization and further analysis.\u003c/p\u003e\n"]]],["The content demonstrates ordinary least squares (OLS) regression on a Landsat 8 image time series using Earth Engine. Key actions include preparing images by masking and scaling, creating predictor and response variables (constant, trend, seasonal, and NDVI), and converting the collection to an array. OLS coefficients are then calculated using three methods: direct matrix operations, pseudo-inverse, and the `matrixSolve()` function. Finally, the coefficient array is projected and flattened into a multi-band image. `matrixSolve()` is highlighted as the most efficient and flexible method.\n"],null,["# Array Transformations\n\nEarth Engine supports array transformations such as transpose, inverse and pseudo-inverse.\nAs an example, consider an ordinary least squares (OLS) regression of a time series of\nimages. In the following example, an image with bands for predictors and a response is\nconverted to an array image, then \"solved\" to obtain least squares coefficients estimates\nthree ways. First, assemble the image data and convert to arrays:\n\n### Code Editor (JavaScript)\n\n```javascript\n// Scales and masks Landsat 8 surface reflectance images.\nfunction prepSrL8(image) {\n // Develop masks for unwanted pixels (fill, cloud, cloud shadow).\n var qaMask = image.select('QA_PIXEL').bitwiseAnd(parseInt('11111', 2)).eq(0);\n var saturationMask = image.select('QA_RADSAT').eq(0);\n\n // Apply the scaling factors to the appropriate bands.\n var opticalBands = image.select('SR_B.').multiply(0.0000275).add(-0.2);\n var thermalBands = image.select('ST_B.*').multiply(0.00341802).add(149.0);\n\n // Replace the original bands with the scaled ones and apply the masks.\n return image.addBands(opticalBands, null, true)\n .addBands(thermalBands, null, true)\n .updateMask(qaMask)\n .updateMask(saturationMask);\n}\n\n// Load a Landsat 8 surface reflectance image collection.\nvar collection = ee.ImageCollection('LANDSAT/LC08/C02/T1_L2')\n // Filter to get only two years of data.\n .filterDate('2019-04-01', '2021-04-01')\n // Filter to get only imagery at a point of interest.\n .filterBounds(ee.Geometry.Point(-122.08709, 36.9732))\n // Prepare images by mapping the prepSrL8 function over the collection.\n .map(prepSrL8)\n // Select NIR and red bands only.\n .select(['SR_B5', 'SR_B4'])\n // Sort the collection in chronological order.\n .sort('system:time_start', true);\n\n// This function computes the predictors and the response from the input.\nvar makeVariables = function(image) {\n // Compute time of the image in fractional years relative to the Epoch.\n var year = ee.Image(image.date().difference(ee.Date('1970-01-01'), 'year'));\n // Compute the season in radians, one cycle per year.\n var season = year.multiply(2 * Math.PI);\n // Return an image of the predictors followed by the response.\n return image.select()\n .addBands(ee.Image(1)) // 0. constant\n .addBands(year.rename('t')) // 1. linear trend\n .addBands(season.sin().rename('sin')) // 2. seasonal\n .addBands(season.cos().rename('cos')) // 3. seasonal\n .addBands(image.normalizedDifference().rename('NDVI')) // 4. response\n .toFloat();\n};\n\n// Define the axes of variation in the collection array.\nvar imageAxis = 0;\nvar bandAxis = 1;\n\n// Convert the collection to an array.\nvar array = collection.map(makeVariables).toArray();\n\n// Check the length of the image axis (number of images).\nvar arrayLength = array.arrayLength(imageAxis);\n// Update the mask to ensure that the number of images is greater than or\n// equal to the number of predictors (the linear model is solvable).\narray = array.updateMask(arrayLength.gt(4));\n\n// Get slices of the array according to positions along the band axis.\nvar predictors = array.arraySlice(bandAxis, 0, 4);\nvar response = array.arraySlice(bandAxis, 4);\n```\nPython setup\n\nSee the [Python Environment](/earth-engine/guides/python_install) page for information on the Python API and using\n`geemap` for interactive development. \n\n```python\nimport ee\nimport geemap.core as geemap\n```\n\n### Colab (Python)\n\n```python\nimport math\n\n\n# Scales and masks Landsat 8 surface reflectance images.\ndef prep_sr_l8(image):\n # Develop masks for unwanted pixels (fill, cloud, cloud shadow).\n qa_mask = image.select('QA_PIXEL').bitwiseAnd(int('11111', 2)).eq(0)\n saturation_mask = image.select('QA_RADSAT').eq(0)\n\n # Apply the scaling factors to the appropriate bands.\n optical_bands = image.select('SR_B.').multiply(0.0000275).add(-0.2)\n thermal_bands = image.select('ST_B.*').multiply(0.00341802).add(149.0)\n\n # Replace the original bands with the scaled ones and apply the masks.\n return (\n image.addBands(optical_bands, None, True)\n .addBands(thermal_bands, None, True)\n .updateMask(qa_mask)\n .updateMask(saturation_mask)\n )\n\n\n# Load a Landsat 8 surface reflectance image collection.\ncollection = (\n ee.ImageCollection('LANDSAT/LC08/C02/T1_L2')\n # Filter to get only two years of data.\n .filterDate('2019-04-01', '2021-04-01')\n # Filter to get only imagery at a point of interest.\n .filterBounds(ee.Geometry.Point(-122.08709, 36.9732))\n # Prepare images by mapping the prep_sr_l8 function over the collection.\n .map(prep_sr_l8)\n # Select NIR and red bands only.\n .select(['SR_B5', 'SR_B4'])\n # Sort the collection in chronological order.\n .sort('system:time_start', True)\n)\n\n\n# This function computes the predictors and the response from the input.\ndef make_variables(image):\n # Compute time of the image in fractional years relative to the Epoch.\n year = ee.Image(image.date().difference(ee.Date('1970-01-01'), 'year'))\n # Compute the season in radians, one cycle per year.\n season = year.multiply(2 * math.pi)\n # Return an image of the predictors followed by the response.\n return (\n image.select()\n .addBands(ee.Image(1)) # 0. constant\n .addBands(year.rename('t')) # 1. linear trend\n .addBands(season.sin().rename('sin')) # 2. seasonal\n .addBands(season.cos().rename('cos')) # 3. seasonal\n .addBands(image.normalizedDifference().rename('NDVI')) # 4. response\n .toFloat()\n )\n\n\n# Define the axes of variation in the collection array.\nimage_axis = 0\nband_axis = 1\n\n# Convert the collection to an array.\narray = collection.map(make_variables).toArray()\n\n# Check the length of the image axis (number of images).\narray_length = array.arrayLength(image_axis)\n# Update the mask to ensure that the number of images is greater than or\n# equal to the number of predictors (the linear model is solvable).\narray = array.updateMask(array_length.gt(4))\n\n# Get slices of the array according to positions along the band axis.\npredictors = array.arraySlice(band_axis, 0, 4)\nresponse = array.arraySlice(band_axis, 4)\n```\n\nNote that `arraySlice()` returns all the images in the time series for the\nrange of indices specified along the `bandAxis` (the 1-axis). At this point,\nmatrix algebra can be used to solve for the OLS coefficients:\n\n### Code Editor (JavaScript)\n\n```javascript\n// Compute coefficients the hard way.\nvar coefficients1 = predictors.arrayTranspose().matrixMultiply(predictors)\n .matrixInverse().matrixMultiply(predictors.arrayTranspose())\n .matrixMultiply(response);\n```\nPython setup\n\nSee the [Python Environment](/earth-engine/guides/python_install) page for information on the Python API and using\n`geemap` for interactive development. \n\n```python\nimport ee\nimport geemap.core as geemap\n```\n\n### Colab (Python)\n\n```python\n# Compute coefficients the hard way.\ncoefficients_1 = (\n predictors.arrayTranspose()\n .matrixMultiply(predictors)\n .matrixInverse()\n .matrixMultiply(predictors.arrayTranspose())\n .matrixMultiply(response)\n)\n```\n\nAlthough this method works, it is inefficient and makes for difficult to read code. A\nbetter way is to use the `pseudoInverse()` method\n(`matrixPseudoInverse()` for an array image):\n\n### Code Editor (JavaScript)\n\n```javascript\n// Compute coefficients the easy way.\nvar coefficients2 = predictors.matrixPseudoInverse()\n .matrixMultiply(response);\n```\nPython setup\n\nSee the [Python Environment](/earth-engine/guides/python_install) page for information on the Python API and using\n`geemap` for interactive development. \n\n```python\nimport ee\nimport geemap.core as geemap\n```\n\n### Colab (Python)\n\n```python\n# Compute coefficients the easy way.\ncoefficients_2 = predictors.matrixPseudoInverse().matrixMultiply(response)\n```\n\nFrom a readability and computational efficiency perspective, the best way to get the OLS\ncoefficients is `solve()` (`matrixSolve()` for an array image). The\n`solve()` function determines how to best solve the system from characteristics\nof the inputs, using the pseudo-inverse for overdetermined systems, the inverse for square\nmatrices and special techniques for nearly singular matrices:\n\n### Code Editor (JavaScript)\n\n```javascript\n// Compute coefficients the easiest way.\nvar coefficients3 = predictors.matrixSolve(response);\n```\nPython setup\n\nSee the [Python Environment](/earth-engine/guides/python_install) page for information on the Python API and using\n`geemap` for interactive development. \n\n```python\nimport ee\nimport geemap.core as geemap\n```\n\n### Colab (Python)\n\n```python\n# Compute coefficients the easiest way.\ncoefficients_3 = predictors.matrixSolve(response)\n```\n\nTo get a multi-band image, project the array image into a lower dimensional space, then\nflatten it:\n\n### Code Editor (JavaScript)\n\n```javascript\n// Turn the results into a multi-band image.\nvar coefficientsImage = coefficients3\n // Get rid of the extra dimensions.\n .arrayProject([0])\n .arrayFlatten([\n ['constant', 'trend', 'sin', 'cos']\n]);\n```\nPython setup\n\nSee the [Python Environment](/earth-engine/guides/python_install) page for information on the Python API and using\n`geemap` for interactive development. \n\n```python\nimport ee\nimport geemap.core as geemap\n```\n\n### Colab (Python)\n\n```python\n# Turn the results into a multi-band image.\ncoefficients_image = (\n coefficients_3\n # Get rid of the extra dimensions.\n .arrayProject([0]).arrayFlatten([['constant', 'trend', 'sin', 'cos']])\n)\n```\n\nExamine the outputs of the three methods and observe that the resultant matrix of\ncoefficients is the same regardless of the solver. That `solve()` is flexible\nand efficient makes it a good choice for general purpose linear modeling."]]