Primeiros passos usando Google Earth Engine com Python

Confira nosso curso online de QGIS

Aprenda como carregar imagens e geometrias no Google Earth Engine usando o Google Colab. Veja também como visualizar os seus mapas e como calcular o índice NDVI.

O Google Earth Engine é uma plataforma online para o desenvolvimento de análises espaciais usando um extenso banco de imagens aéreas, tudo de forma otimizada para que estas análises possam ser globais.

Nesta postagem vamos dar os passos iniciais para você começar a usar o Google Earth Engine (GEE) com a linguagem de programação Python.

Você pode tanto usar o Python instalado no seu computador ou no Google Colab. Neste tutorial, sugerimos que você utilize o Google Colab, para pularmos a parte de instalação do GEE no seu computador. Caso você ainda tenha interesse em instalar o GEE, confira aqui a documentação sobre a instalação ou veja esse tutorial do Instrutor GIS.

O Google Colab funciona como um Jupyter Notebook, onde diferentes linhas de código podem ser executados em diferentes células, facilitando a avaliação dos resultados obtidos.

Para acessá-lo, vá no seu Google Drive e clique em “+ Novo”, vá em “mais” e selecione “Google Colaboratory”. Caso ele não esteja aparecendo, clique em “+ conectar mais apps” e busque por Colaboratory (e em seguida, instale ele).

Autenticação do Acesso no GEE

Após criar um arquivo do Colaboratory (Google Colab), vamos inserir nossos códigos nele.

Lembre-se que para usar o Google Earth Engine, você deverá ter uma conta aprovado no site dele, pois para utilizar as suas funções, é necessário autenticar seu acesso.

Para carregar a biblioteca do GEE e autenticar seu acesso, você deverá escrever e executar a célula com os seguintes comandos:

import ee
ee.Authenticate()
ee.Initialize()

Um link será gerado para você e você deverá escolher a sua conta gmail que contém acesso ao GEE. Após isso, copie o código gerado e cole no quadro abaixo da célula que acabamos de executar. Se tudo der certo, a mensagem “Successfully saved authorization token” aparecerá para você.

Carregando imagens no GEE

Há vários conjuntos de imagens no GEE. Você pode consultar o catálogo clicando aqui. Note que, conforme você acessa um determinado conjunto de imagens, estará disponível na página da imagens sua identificação, a qual você deverá usar para acessar as imagens, tais como os exemplos abaixo:

  • LANDSAT/LC08/C01/T1_SR
  • MODIS/006/MOD09GQ
  • COPERNICUS/S2_SR

Além disso, temos duas formas de acessar as imagens. Temos as imagens propriamente ditas (ee.Image) e as coleções (ee.ImageCollection). A primeira são imagens únicas, apenas a imagem solicitada, e as coleções envolvem várias imagens.

Vamos carregar uma imagem LANDSAT 8, considerando a localização da cidade de Siderópolis (SC). Como não sabemos o WRS Path e Row da nossa imagem, vamos carregar nossa imagem considerando uma coordenada da nossa área de interesse.

O código abaixo irá carregar uma coleção de imagens considerando filtros de data e localização. Em seguida, iremos imprimir as informações sobre quantas imagens estão nela.

imagem = ee.ImageCollection('LANDSAT/LC08/C01/T1_SR')\
  .filterDate('2019-01-01','2020-01-01')\
  .filterBounds(ee.Geometry.Point(-49.459937, -28.5919285))

print("Quantidade de Imagens: ", imagem.size().getInfo())

Veja que após chamarmos a função ImageCollection, ela é seguida de outras para realizar a filtragem. Note que usamos a função ee.Geometry.Point() para indicar a localização da nossa área de estudo.

No Earth Engine, muitas das informações estão salvas no servidor, logo, para acessá-las é necessário usar a função getInfo().

Agora que já criamos uma variável contendo as imagens da nossa área de estudo, vamos visualizá-la. Há várias formas de visualizar imagens do Earth Engine em python, porém, no nosso tutorial, vamos realizar uma usando a biblioteca Folium e o código apresentado por Cesar Aybar.

import folium

def Mapdisplay(center, dicc, Tiles="OpensTreetMap",zoom_start=10):
    mapViz = folium.Map(location=center,tiles=Tiles, zoom_start=zoom_start)
    for k,v in dicc.items():
      if ee.image.Image in [type(x) for x in v.values()]:
        folium.TileLayer(
            tiles = v["tile_fetcher"].url_format,
            attr  = 'Google Earth Engine',
            overlay =True,
            name  = k
          ).add_to(mapViz)
      else:
        folium.GeoJson(
        data = v,
        name = k
          ).add_to(mapViz)
    mapViz.add_child(folium.LayerControl())
    return mapViz

Lembre-se que nosso mapa contém várias imagens que estão distribuidas ao longo de um período de tempo, logo, para visualizarmos elas, precisamos convertê-las para uma imagem só. Isso será feito usando a função mediana (median()).

Além disso, também iremos criar um dicionário com o nome da camada que será carregada e as bandas que vamos selecionar. Vamos definir também a coordenada central do nosso mapa e o nível de zoom. Confira o código abaixo.

mediana = imagem.median()

dicionario = {
    'Mediana' : mediana.getMapId({'bands': ['B4', 'B3', 'B2'], 'min': 0, 'max': 3000})
}

centro = [-28.5919285, -49.459937]
Mapdisplay(centro, dicionario, zoom_start= 12)
Visualização das imagens usando o Google Colab.

Neste caso, apresentamos valores medianos na nossa imagem, mas vamos supor que queremos apresentar os dados “originais”. Para isso, precisaremos definir uma data específica e obter o WRS Path e Row.

Você pode obter o WRS Path e Row do satélite LANDSAT para sua área de estudo com a ferramenta LANDSAT Acquisition Tool (https://landsat.usgs.gov/landsat_acq#convertPathRow).

Já temos uma coleção de imagens. Agora vamos ver quais as datas das imagens desta coleção a partir da função elaborada por Vicent, conforme código abaixo.

def ymdList(imgcol):
    def iter_func(image, newlist):
        date = ee.Number.parse(image.date().format("YYYYMMdd"));
        newlist = ee.List(newlist);
        return ee.List(newlist.add(date).sort())
    ymd = imgcol.iterate(iter_func, ee.List([]))
    return list(ee.List(ymd).reduce(ee.Reducer.frequencyHistogram()).getInfo().keys())

Após rodarmos essa função, poderemos rodar o seguinte código.

print('Datas disponíveis: ', ymdList(imagem))

Após obter uma data disponível (neste caso, escolhemos 2019-12-30) e o WRS Path e Row (220 e 080, respectivamente), vamos carregar uma imagem e visualizar algumas das suas propriedades (e.g. Bandas e Cobertura de nuvens).

imagem_unica = ee.Image('LANDSAT/LC08/C01/T1/LC08_220080_20191230')

print('Bandas: ', imagem_unica.bandNames().getInfo())
print('Cobertura de Nuvens (%): ', imagem_unica.get('CLOUD_COVER').getInfo())

dicio2 = imagem_unica.getMapId({'bands': ['B4', 'B3', 'B2'], 'min': 0, 'max': 30000})

Mapdisplay(centro, {'LANDSAT': dicio2})

Com estes códigos, agora você consegue carregar imagens de diferentes satélites e adquirir imagens de dias específicos. Note que para a imagem LANDSAT 8, a nomenclatura das imagens isoladas segue o seguinte principio: LC08 + WRS Path + Row + Data.

Carregando Feições no GEE

No GEE também é possível carregar feições como pontos, linhas e polígonos. O código para gerar cada um delas é o seguinte:

  • Pontos: ee.Geometry.Point([-49.4, -28.6]);
  • Linhas: ee.Geometry.LineString([[-49.4, -28.6], [-49.3, -28.5], [-49.2, -28.4]]);
  • Polígonos: ee.Geometry.Polygon([[-49.4, -28.6], [-49.3, -28.5], [-49.2, -28.4], [-49.4, -28.6]]);

A partir dos exemplos assim, vamos definir algumas variáveis e vamos visualizá-las no mapa.

ponto = ee.Geometry.Point([-49.4, -28.6])
linha = ee.Geometry.LineString([[-49.4, -28.6], [-49.0, -28.6], [-49.0, -28.2]])
poligono = ee.Geometry.Polygon([[-49.4, -28.6], [-49.0, -28.6], [-49.0, -28.2], [-49.4, -28.6]]);

ponto_info = ponto.getInfo()
linha_info = linha.getInfo()
poligono_info = poligono.getInfo()

Mapdisplay(centro, {'Ponto': ponto_info, 'Linha': linha_info, 'Polígono': poligono_info})

Além das geometrias apresentadas, você também consegue criar geometrias do tipo retângulo (ee.Geometry.Rectangle()) e linhas fechadas (ee.Geometry.LinearRing()).

Cálculo de NDVI no Earth Engine

Agora que sabemos como manusear algumas geometrias e imagens no Earth Engine, vamos visualizar como realizar cálculos usando as imagens carregadas. Neste exemplo, vamos mostrar como calcular o NDVI (Normalized Difference Vegetation Index).

Há diferentes formas de calcular o NDVI no Earth Engine, a mais fácil é chamando a função normalizedDifference(). Porém, vamos mostrar como usar a função expressão que possibilita maior flexibilidade para os cálculos. Confira o exemplo abaixo.

NDVI = imagem_unica.expression(
      '(NIR - RED) / (NIR + RED)', {
          'RED': imagem_unica.select('B4'), 
          'NIR': imagem_unica.select('B5')})

NDVI_mapa = {'min': 0, 'max': 1, 'palette': ['FF0000', '00FF00']}
visualizacao = {"NDVI": NDVI.getMapId(NDVI_mapa)}

Mapdisplay(centro, visualizacao)

Veja que a função expression() é interessante pois ela possibilita arranjar as bandas da sua imagem em uma expressão matemática, possibilitando o cálculo de diferentes índices.

Visualização da nossa área de estudo usando o índice NDVI.

Agora que você aprendeu algumas funções para utilizar o Google Earth Engine, pratique, mude a área de estudo, aplique novas expressões e faça testes. Caso tenha ficado com alguma dúvida, fique a vontade para deixar ela nos comentários que responderemos assim que possíve.

Fontes Consultadas.

Cesar Aybar. A series of Jupyter notebook to learn Google Earth Engine with Python. Disponível em <https://github.com/csaybar/EEwPython>. Acesso em 28 jun. 2020.


Clique na figura abaixo e assine nossa lista de emails para receber nosso ebook "Como criar mapas de localização com ArcGIS 10.x".

Apostila Mapa de Localização Banner

Author: Fernando BS

Engenheiro Ambiental e de Segurança do Trabalho. Atua nas áreas de geoprocessamento, mineração e hidrologia. Busca soluções utilizando softwares como QGIS, R e Python.

10 thoughts on “Primeiros passos usando Google Earth Engine com Python”

  1. Primeiro queria agradecer as explicações, elas são bem claras e muito bem elaboradas. Gostaria de poder tirar a seguinte duvida.
    As coordenadas, que estão dentro do ee.Geometry.Point, são as responsaveis por retornar as imagens da area que desejo, correto? Segue a parte do seu codigo.

    imagem = ee.ImageCollection(‘LANDSAT/LC08/C01/T1_SR’)\
    .filterDate(‘2019-01-01′,’2020-01-01’)\
    .filterBounds(ee.Geometry.Point(-49.459937, -28.5919285))
    Caso for isso mesmo que eu entendi, saberia me informar por qual motivo ele não encontra imagens quando insiro a coordenada que eu desejo?

    1. Bom dia Gustavo, obrigado pelo comentário.

      Com relação à sua dúvida, sim, o filterBounds() irá obter as imagens que são ‘tocadas’ pela geometria. Com relação ao seu erro, caso você esteja usando o mesmo código que o nosso, ao rodar ‘imagem.size().getInfo()’, você irá obter 21 imagens. Caso você tenha alterado os parâmetros, confira se o nome da coleção esta correto, se o intervalo de datas é muito pequeno ou esta fora do intervalo atendido pela coleção de imagens, ou se as coordenadas estão corretas. Você tem alguma mensagem de erro ao executar o seu código?

      1. Fala Fernando, eu que estava fazendo coisa errada cara kkkk… Estou aprendendo agora sobre coordenadas e essas referencias, sou estudante de sistemas de informação e estou desenvolvendo um estudo utilizando as imagens do LANDSAT. Meu erro foi bem juvenil, mas vou deixar aqui, vai que mais alguém erra isso.
        No google maps ele dá as coordenadas ao contrario do que é utilizado na função filterBounds, eu não tinha percebido isso. Obrigado pela disposição em ajudar amigo.
        Vi que vocẽs oferecem curso em diversas areas, mas não achei nada de python utilizando as imagens de satelite, teria algum curso nesse sentido? Se tiver me envie o link, pois tenho interesse. Obrigado novamente e até mais

        1. Legal Gustavo, caso precise de alguma ajuda é só comentar. Obrigado por deixar sua resolução do problema, já tive esse problema também, na variável ‘centro’ do tutorial também tem as coordenadas ao contrário do filterBounds – E se você colocar trocado, vai parar lá no meio do mar.

          Com relação à cursos, não temos nada com Python. Mas você pode conferir o blog e canal do Saul Montoya do Hatari Labs, ele posta alguns materiais sobre o tema (https://www.youtube.com/channel/UCGAgjGCEH2SDl12M91D-10Q). Além disso, você pode buscar por tutoriais sobre o pacote Rasterio, que trabalha com raster geoespaciais.

  2. Obrigada pelas dicas, copiei e colei mas no meu caso não deu certo, saberia dizer porque?

    o código
    imagem = ee.ImageCollection(‘LANDSAT/LC08/C01/T1_SR’)\
    .filterDate(‘2019-01-01′,’2020-01-01’)\
    .filterBounds(ee.Geometry.Point(-49.459937, -28.5919285))
    print(“Quantidade de Imagens: “, imagem.size().getInfo())

    retorna o seguinte erro: SyntaxError: Expecting Unicode escape sequence \uXXXX (2:54)

    após eu tirar as barras \ da linha 1 e 2 continuou com erro ->Variable must be declared with “var”: imagem

    1. Bom dia Elisa,

      Acredito que você esta utilizando Editor online do Earth Engine. Nele, você deverá usar a linguagem de prograçãma JavaScript. O nosso tutorial é para Python. Caso você pretenda continuar usando JavaScript, você pode conferir o material do Luis Sadeck no youtube (https://www.youtube.com/playlist?list=PLNFvG6bTA4NReWtgC93Mh9Tw1RNG4EBMP). Caso queira usar Python, confira o Google Colab (https://colab.research.google.com/) para rodar os códigos.

  3. Fernando, bom dia.

    Parabéns pela postagem, sou iniciante tanto em Python como no GEE, estou tentando usar seu código para visualizar os dados da região onde trabalho, porém encontro o seguinte erro ao tentar carregar uma imagem única (estou utilizando as datas mostradas no print):

    —————————————————————————
    HttpError Traceback (most recent call last)
    /usr/local/lib/python3.6/dist-packages/ee/data.py in _execute_cloud_call(call, num_retries)
    344 try:
    –> 345 return call.execute(num_retries=num_retries)
    346 except googleapiclient.errors.HttpError as e:

    5 frames
    HttpError:

    During handling of the above exception, another exception occurred:

    EEException Traceback (most recent call last)
    /usr/local/lib/python3.6/dist-packages/ee/data.py in _execute_cloud_call(call, num_retries)
    345 return call.execute(num_retries=num_retries)
    346 except googleapiclient.errors.HttpError as e:
    –> 347 raise _translate_cloud_exception(e)
    348
    349

    EEException: Image.load: Image asset ‘LANDSAT/LC08/C01/T1/LC08_220080_20190108’ not found.

    Sabe me dizer o que poderia ser a causa?

    1. Boa noite Marcus Vinicius, obrigado pelo comentário.
      Possivelmente para a região onde você trabalha essa data não tem imagem disponível. O Landsat 8 tem imagens a cada 15 dias, sendo que as datas podem variar conforme a região. Você pode utilizar a função ymdlist junto com uma coleção de imagens para filtrar um período de tempo e depois selecionar uma data específica para a sua localidade.

  4. Olá! Ótimo artigo, tem me ajudado bastante para conseguir meus primeiros resultados no GEE.
    Gostaria de saber: juntamente com este script para acessar as coleções do Landsat, é possível instalar bibliotecas como matplotlib, spectral e tifffile para fazer análises de reflectância, visualizar histogramas e criar mapas com dados do GEE acessado pelo Google Colab?

    Muito obrigado!

Deixe um comentário para Gustavo Cancelar resposta

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *