Alura > Cursos de Data Science > Cursos de Engenharia de Dados > Conteúdos de Engenharia de Dados > Primeiras aulas do curso PySpark: processamento e modelagem em larga escala

PySpark: processamento e modelagem em larga escala

Fundamentos do Spark e PySpark - Apresentação

Apresentando o instrutor e o curso

Olá! Meu nome é Vitor Mello. Sou um homem de pele morena, com 1,87 m de altura, estou usando uma camiseta verde e óculos graduados. Atrás de mim, há uma parede com uma estante metálica. Vou te acompanhar neste curso de PySpark.

Audiodescrição: Vitor é um homem de pele morena, com 1,87 m de altura, usando uma camiseta verde e óculos graduados. Atrás dele, há uma parede com uma estante metálica.

Descrevendo o conteúdo do curso

Neste curso, veremos como processar grandes volumes de dados e criar modelos, tanto de regressão quanto de classificação, utilizando PySpark. Recomendamos que se tenha conhecimentos de SQL e Python para aproveitar ao máximo este curso.

Ao final do curso, seremos capazes de ler diferentes tipos de dados, como CSV, JSON e Parquet, além de utilizar tanto a API do PySpark quanto SQL puro para processar dados. Também veremos como criar pipelines, pipelines de modelagem, treinar modelos de regressão ou de classificação, otimizar os hiperparâmetros e, ao final, salvar a pipeline. Utilizaremos, para seguir todo esse fluxo, dados do e-commerce brasileiro Olist.

Encerrando a introdução

Na próxima aula, começaremos com uma introdução sobre o Spark. Nos vemos lá. Muito obrigado.

Fundamentos do Spark e PySpark - Conhecendo Spark

Introduzindo conceitos de Spark

Olá. Bem-vindo a este vídeo. Hoje faremos a introdução dos conceitos necessários de Spark para que possamos trabalhar.

Ao observarmos estas diapositivas, podemos nos perguntar: qual é a diferença entre PySpark e Spark? O nome completo seria Apache Spark. Quando trabalhamos com Spark em Python, chamamos de PySpark. Outra informação importante é que a maior parte do código, o núcleo do Spark, foi escrito em Scala. No entanto, podemos utilizá-lo em Java, R e Python.

Explorando a estrutura e arquitetura do Spark

Dentro do Spark, temos módulos como o de processamento de dados, que neste caso é o Spark SQL, de aprendizado de máquina, que seria o MLlib, e de streaming de dados, ou seja, Structured Streaming. Neste curso, falaremos sobre Python, processamento de dados com Spark SQL e treinamento com MLlib.

Essa é, em linhas gerais, a estrutura do Spark. Existem conceitos importantíssimos da arquitetura do Spark que serão relevantes para nós. O Spark resolve um problema de processamento de dados distribuídos entre várias máquinas. Quando falamos de várias máquinas, nos referimos a um cluster. No Spark, teremos as máquinas que chamaremos de Workers, que realmente farão o processamento de dados, e o Driver, que provavelmente é a máquina que recebe nossa solicitação ou consulta.

Explicando o funcionamento do cluster no Spark

Por exemplo, ao utilizarmos o Databricks, que é uma plataforma popular para Spark, escrevemos uma consulta e a executamos. Provavelmente, o local onde executamos não é o Driver; ainda assim, é chamado de Driver. Existe um Cluster Manager que gerencia o número de Workers e a distribuição de carga entre eles. O Driver fará a requisição, os Workers processarão e devolverão os dados ao Driver. Essa é a estrutura à qual nos referimos em relação ao cluster.

Quando executamos localmente, o Spark utiliza a mesma abstração; no entanto, os Workers não são mais computadores dentro de um cluster, mas sim threads. Nesse caso, teremos um thread dedicado ao Driver e outros threads serão os Workers. Por exemplo, se nossa máquina possui quatro threads, um deles será o Driver e os outros serão os Workers. Assim, podemos paralelizar o processamento de dados dentro da própria máquina.

Configurando o ambiente no Google Colab

Esses são alguns dos conceitos que queríamos abordar. Agora, veremos na prática como funciona a plataforma que utilizaremos neste curso, que é o Google Colab. No Google Colab, mostraremos algumas configurações necessárias para que o Spark funcione, como o Java. Utilizaremos o Java 17 e o Python 3.12.

Para verificar a versão do Java instalada, podemos usar o seguinte comando no Google Colab:

!java --version

E para verificar a versão do Python, utilizamos:

!python --version

Demonstrando a criação de uma Spark Session

Trouxemos um exemplo para a próxima aula, onde discutiremos o que é uma Spark Session. Queremos mostrar um dataset para que tenhamos uma ideia de como funciona. Sempre que trabalharmos com Spark e quisermos visualizar um dado, a tabela terá um aspecto semelhante ao que veremos. Utilizaremos o Google Colab. Como comentado, também existe o Databricks, que é outra plataforma. Neste caso, estamos usando a versão gratuita. Funciona de maneira semelhante, se desejarmos. É uma plataforma bastante conhecida para uso com Spark.

Para iniciar uma sessão Spark e criar um DataFrame simples, usamos o seguinte código:

from pyspark.sql import SparkSession

spark = SparkSession.builder.getOrCreate()
df = spark.createDataFrame([(1, "Alice"), (2, "Bob")], ["id", "name"])
df.show()

Comparando visualizações no Databricks e Google Colab

No Databricks, teremos o Java, a rota do Java, e o Python, cuja versão também é 3.12. A visualização é um pouco diferente. Podemos notar que a tabela não está em texto plano, mas possui uma interface mais amigável. Podemos executar o df.show() e obter os dados da mesma forma que no Google Colab, e também ao executar localmente.

Sobre a instalação do PySpark localmente, deixaremos as instruções por escrito. Assim, podemos segui-las no próximo conteúdo do curso. Obrigado.

Fundamentos do Spark e PySpark - Spark Session

Discutindo a Spark Session

Hoje vamos discutir sobre a Spark Session, ou seja, as sessões do Spark. O que é isso? É o nosso ponto de entrada unificado para as funcionalidades do Spark. Isso significa que nos permite usar os métodos da API do Spark. Podemos traçar um paralelo com o uso do pandas, quando lemos um arquivo CSV, por exemplo, com pd.read_csv. Aqui, funciona de maneira semelhante.

Existem dois pontos avançados que gostaria de comentar, sem entrar em detalhes, mas é importante mencionar que é possível configurar nosso hardware na sessão do Spark. Por exemplo, se estivermos executando com vários workers e quisermos limitar a quantidade de memória utilizada, podemos fazer isso nas configurações da sessão. Ou, se estivermos usando localmente e quisermos que o driver utilize 100% do nosso computador, podemos configurar isso no hardware. Normalmente, não se usa 100%, deixando um pouco para o sistema operacional.

Explorando funcionalidades da Spark Session

Outra função do Spark, que não configuramos, é a distribuição da carga de trabalho entre os clusters. Essas são algumas das funcionalidades que a Spark Session oferece.

Ao longo da aula, vamos mostrar como inicializar e criar um DataFrame. Nas próximas aulas, abordaremos como fazer a leitura e como salvar arquivos, o que também envolverá a questão da Spark Session. Vamos iniciar uma sessão aqui. Primeiro, precisamos importar a SparkSession do módulo pyspark.sql:

from pyspark.sql import SparkSession

Inicializando a Spark Session

Em seguida, executamos para ver o que foi importado. Guardamos na variável spark, o que é uma boa prática. A maioria dos códigos que lemos sobre Spark estará guardada em uma variável com esse nome. Inicialmente, definimos a variável spark:

spark = 

Agora, vamos completar a inicialização da Spark Session. A SparkSession possui um método chamado Builder, que não pode ser usado sozinho; precisamos de outro método que indique o que queremos fazer. Primeiro, configuramos o Builder:

spark = SparkSession

E então, utilizamos o método builder:

spark = SparkSession.builder

O mais clássico é usar getOrCreate, que pega uma sessão existente ou cria uma nova:

spark = SparkSession.builder.getOrCreate()

Verificando a execução local no Google Colab

Pronto, Spark criado. Um ponto a destacar sobre o Google Colab: ao executar isso, saberemos onde está sendo executado, se em um cluster ou localmente. Mesmo no Google Colab, que utiliza uma máquina na nuvem, estamos executando localmente, pois não é um conjunto de computadores, mas sim uma única máquina. Por isso, aparecerá como local. Podemos verificar isso com o seguinte comando:

# Só para mostrar que estamos rodando o spark localmente - não em um conjunto de computadores (cluster)
spark.sparkContext.master

Criando DataFrames a partir de dados de exemplo

Agora que aprendemos a criar uma Spark Session, vamos descobrir como criar DataFrames a partir de dados de exemplo. Usaremos bastante durante o curso, principalmente para exemplificar conceitos complexos, como funções Window e joins. Para não visualizar todo o dataset, que pode ter, por exemplo, 300 linhas, podemos criar um dataset menor para entender o comportamento.

Criamos uma tabela com três colunas e duas linhas: nome, data de nascimento e nota. Vamos criar nosso dado, nossa tabela, e guardá-la na variável df. Primeiro, definimos os dados e as colunas:

data = [
    ("João","30/05/1998", 10.0),
    ("Ana", "19/05/2000", 9.5),
]
columns = ["nome","nascimento","nota"]

Criando e exibindo o DataFrame

Agora, vamos criar o DataFrame usando a sessão Spark:

df = 

E então, completamos a criação do DataFrame:

df = spark.createDataFrame(data, columns)

Executamos e agora vamos mostrar esse df:

df.show()

Analisando o esquema do DataFrame

Vamos analisar os dados. Eles coincidem 100% com o que está aqui. Agora, como verificamos os tipos? Não sabemos se essa data está como String (cadeia de caracteres) ou como data realmente. Vamos imprimir nosso esquema:

df.printSchema()

O nome está como String, a nota está como número, mas o nascimento está como String. Esse é um ponto que precisaremos tratar. Nas próximas aulas, descobriremos como fazer isso.

Explicando o conceito de Lazy Evaluation

Gostaríamos de comentar um conceito importantíssimo do Spark, que é o Lazy Evaluation (avaliação preguiçosa). Não é preguiçoso por ser lento, mas porque é planejado. Vamos fazer um paralelo: imagine que estamos em um restaurante e um garçom vai anotar nosso pedido. Vamos pedir três coisas. Agora, imagine que o garçom é ansioso. Cada vez que pedimos algo, ele vai até a cozinha. O que o Spark faz é esperar até que façamos todos os pedidos para só então executar, quando dissermos que está tudo bem. Ele faz o pedido na cozinha de todos os itens que queremos. Essa é a ideia do Lazy Evaluation.

Vamos entender o que isso significa. As transformações são executadas apenas quando necessário, ou seja, quando uma ação é executada. O que é uma transformação? É um método que devolve um DataFrame. Quando falamos de fazer o pedido, estamos fazendo um SQL, selecionando colunas, fazendo JOIN, GROUP BY, tudo isso devolve um DataFrame. Não está sendo executado, apenas avaliando se o código funciona e criando um plano de execução, mas não o executa. Só executa quando uma ação é realizada, como um .count ou um .show. Isso resulta em um código mais otimizado no processo de interação.

Explorando o Catalyst Optimizer

Imagine que estamos em um notebook, isso é muito comum, e estamos fazendo nosso SQL, executando apenas para ver se as coisas fazem sentido, mas não estamos mostrando os dados. Apenas verificamos se a sintaxe está correta. Dessa forma, garantimos o uso do Lazy Evaluation. No entanto, cada vez que executamos e colocamos um .show, não estamos sendo tão amigáveis com o Spark, não estamos aproveitando ao máximo. Se estamos interagindo com o código apenas para validar a sintaxe, seria bom remover o .count e o .show, apenas para ver se o Spark pode executá-lo. Assim, ele pode otimizar nosso SQL, selecionando apenas o que precisa ser executado.

Outro ponto sobre o Lazy Evaluation é o Catalyst Optimizer. Ele lê nosso plano de execução e organiza as coisas na ordem correta. Por exemplo, em SQL padrão, temos uma ordem correta das coisas que devemos definir: SELECT, de onde selecionamos, qual filtro aplicamos. No Spark, não existe essa ordem. Podemos fazer um SELECT, um GROUP BY, um JOIN e depois um FILTER no final. Podemos colocar na ordem que quisermos. Mas o Spark lerá, planejará nossa query e mudará um pouco a ordem de forma que seja mais conveniente para otimizar, obtendo um resultado final igual ao que pensamos, mas otimizado. Essa é a vantagem do Lazy Evaluation.

Concluindo a aula sobre Spark Session

Esses eram os conceitos que queríamos transmitir. Também vimos como criar uma sessão. Isso é tudo por hoje. Na próxima aula, veremos como ler arquivos.

Sobre o curso PySpark: processamento e modelagem em larga escala

O curso PySpark: processamento e modelagem em larga escala possui 186 minutos de vídeos, em um total de 57 atividades. Gostou? Conheça nossos outros cursos de Engenharia de Dados em Data Science, ou leia nossos artigos de Data Science.

Matricule-se e comece a estudar com a gente hoje! Conheça outros tópicos abordados durante o curso:

Aprenda Engenharia de Dados acessando integralmente esse e outros cursos, comece hoje!

Conheça os Planos para Empresas