Alura > Cursos de Data Science > Cursos de Excel > Conteúdos de Excel > Primeiras aulas do curso Python: normalizando arquivos JSON

Python: normalizando arquivos JSON

Normalizando arquivos JSON - Normalizando arquivos JSON

Olá! Me chamo Mirla Costa, e sou instrutora da Alura.

Audiodescrição: Mirla se descreve como uma mulher de pele clara, com cabelos cacheados e pretos, que caem abaixo da altura dos ombros. Ela usa óculos de grau com armação redonda e veste uma camisa preta lisa. Ao fundo, duas prateleiras flutuantes com livros e decorações são visíveis.

Normalizando arquivos JSON

Neste vídeo, iremos relembrar como normalizar arquivos JSON para transformá-los em dataframes, de forma que possam ser manipulados em projetos de data science.

Um notebook com todo o material que será apresentado, incluindo alguns dados, está disponível para que você possa acessar todo o conteúdo exibido.

Iniciaremos com o notebook. Ao nos referirmos a arquivos JSON, falamos de um formato que armazena dados em pares de chaves e valores, em um formato de dicionário, como já conhecemos no Python. Para exemplificar, temos o arquivo_1.json salvo na seção de "Arquivos" do Google Colab.

Vamos abri-lo para observar que todos os valores de colunas e elementos dessas colunas estão organizados em dicionários e grupos de pares chave-valor:

[
    {
        "id_vendedor": 101,
        "id_cliente": 1001,
        "produto": "Notebook",
        "quantidade": 1,
        "valor_unitario": 3500.00,
        "valor_total": 3500.00
    },
    {
        "id_vendedor": 102,
        "id_cliente": 1002,
        "produto": "Smartphone",
        "quantidade": 2,
        "valor_unitario": 1200.00,
        "valor_total": 2400.00
    },
    {
        "id_vendedor": 103,
        "id_cliente": 1003,
        "produto": "Monitor",
        "quantidade": 3,
        "valor_unitario": 800.00,
        "valor_total": 2400.00
    }
]

Para importar esse arquivo e transformá-lo em um dataframe manipulável, utilizamos a biblioteca Pandas. Em uma célula do Google Colab, digitamos:

import pandas as pd

Para ler o arquivo e convertê-lo em um dataframe, usamos a função pd.read_json(), fornecendo o caminho do arquivo.

df = pd.read_json('arquivo_1.json')
df
-id_vendedorid_clienteprodutoquantidadevalor_unitariovalor_total
01011001Notebook135003500
11021002Smartphone212002400
21031003Monitor38002400

Ao executar, o resultado será o dataframe que pode ser trabalhado em projetos.

Dicionários aninhados

Contudo, esse não é o único tipo de arquivo JSON possível. Também existem arquivos com dicionários aninhados, como o arquivo_2.json.

[
    {
        "id_vendedor": 101,
        "id_cliente": 1001,
        "detalhes_compra": {
            "produto": "Notebook",
            "quantidade": 1,
            "valor_unitario": 3500.00,
            "valor_total": 3500.00
        }
    },
    {
        "id_vendedor": 102,
        "id_cliente": 1002,
        "detalhes_compra": {
            "produto": "Smartphone",
            "quantidade": 2,
            "valor_unitario": 1200.00,
            "valor_total": 2400.00
        }
    },
    {
        "id_vendedor": 103,
        "id_cliente": 1003,
        "detalhes_compra": {
            "produto": "Monitor",
            "quantidade": 3,
            "valor_unitario": 800.00,
            "valor_total": 2400.00
        }
    }
]

Ao abrir esse arquivo, observamos que ele contém um dicionário dentro de outros dicionários, que por sua vez estão em uma lista de dicionários.

Nesse caso, teremos dificuldades em utilizar o pd.read_json(). Ao utilizarmos novamente o pd.read_json() com o arquivo_2.json e executarmos a célula, observamos que o dicionário aninhado no segundo nível se apresenta de forma incorreta, o que impede o acesso aos dados.

df = pd.read_json('arquivo_2.json')
df
-id_vendedorid_clientedetalhes_compra
01011001{'produto': 'Notebook', 'quantidade': 1, 'valor_unitario': 3500, 'valor_total': 3500}
11021002{'produto': 'Smartphone', 'quantidade': 2, 'valor_unitario': 1200, 'valor_total': 2400}
21031003{'produto': 'Monitor', 'quantidade': 3, 'valor_unitario': 800, 'valor_total': 2400}

Isso ocorre porque o read_json() só lê arquivos JSON com dicionários em um único nível. Quando estão aninhados, ele não consegue ler.

Normalizando com pd.json_normalize

É necessário normalizar nossos arquivos JSON. A normalização é realizada com a função pd.json_normalize, do Pandas. Para aplicá-la, não utilizaremos o dataframe recém-criado, pois o json_normalize requer uma lista de dicionários ou um dicionário para aplicar a normalização. Portanto, ao invés de manipular o dataframe, leremos o arquivo_2.json e obter esses dados como uma lista de dicionários.

Para isso, utilizaremos a biblioteca JSON, que é nativa do Python. Faremos o import dessa biblioteca em uma nova célula:

import json

Em uma nova célula, leremos o arquivo_2.json no formato de leitura, especificando 'r' dentro da estrutura with. Armazenaremos o conteúdo em dados usando o comando json.load().

with open('arquivo_2.json', 'r') as arquivo:
    dados = json.load(arquivo)
dados

[{'id_vendedor': 101,

'id_cliente': 1001,

'detalhes_compra': {'produto': 'Notebook',

'quantidade': 1,

'valor_unitario': 3500.0,

'valor_total': 3500.0}},

{'id_vendedor': 102,

'id_cliente': 1002,

'detalhes_compra': {'produto': 'Smartphone',

'quantidade': 2,

'valor_unitario': 1200.0,

'valor_total': 2400.0}},

{'id_vendedor': 103,

'id_cliente': 1003,

'detalhes_compra': {'produto': 'Monitor',

'quantidade': 3,

'valor_unitario': 800.0,

'valor_total': 2400.0}}]

Dessa forma, dados será uma lista de dicionários.

Para normalizar, basta encaminharmos esses dados para a função pd.json_normalize(dados), resultando em um dataframe totalmente manipulável.

df = pd.json_normalize(dados)
df
-id_vendedorid_clientedetalhes_compra.produtodetalhes_compra.quantidadedetalhes_compra.valor_unitariodetalhes_compra.valor_total
01011001Notebook13500.03500.0
11021002Smartphone21200.02400.0
21031003Monitor3800.02400.0

Observamos que existe um separador dentro da coluna onde estavam os dados aninhados, o qual pode ser alterado posteriormente.

Para saber como modificar esse separador, é necessário consultar o material.

Um último detalhe refere-se ao comportamento da função json_normalize quando recebe uma estrutura que não é exatamente um dicionário, como uma nova lista de dicionários. Em uma nova célula, inserimos:

dados = [
            {
                "id_vendedor": 101,
                "id_cliente": 1001,
                "compras": [
                    {"produto": "Notebook", "quantidade": 1, "valor_unitario": 3500.00, "valor_total": 3500.00},
                    {"produto": "Mouse", "quantidade": 2, "valor_unitario": 50.00, "valor_total": 100.00}
                ]
            },
            {
                "id_vendedor": 102,
                "id_cliente": 1002,
                "compras": [
                    {"produto": "Smartphone", "quantidade": 1, "valor_unitario": 1200.00, "valor_total": 1200.00},
                    {"produto": "Fone de Ouvido", "quantidade": 1, "valor_unitario": 200.00, "valor_total": 200.00}
                ]
            }
        ]

A chave "compras" contém uma lista de dicionários com novos dados. Ao executarmos a célula acima e aplicarmos o json_normalize, percebemos que ele não consegue normalizar dicionários dentro de uma nova lista de dicionários, pois ele não expande a normalização quando encontra estruturas diferentes de dicionários, como listas, strings, valores, entre outros.

df = pd.json_normalize(dados)
df
-id_vendedorid_clientecompras
01011001[{'produto': 'Notebook', 'quantidade': 1, 'valor_unitario': 3500.0, 'valor_total': 3500.0}]
11021002[{'produto': 'Smartphone', 'quantidade': 1, 'valor_unitario': 1200.0, 'valor_total': 1200.0}]

Definindo a chave de normalização

Nesse caso, precisamos definir a chave para a normalização, utilizando o parâmetro record_path. Ao utilizar a função json_normalize, enviamos os dados e acrescentamos o parâmetro record_path, indicando a chave que contém a nova lista, no caso, 'compras'. Em uma nova célula, digitamos:

df = pd.json_normalize(dados, record_path='compras')
df
-produtoquantidadevalor_unitariovalor_total
0Notebook13500.03500.0
1Mouse250.0100.0
2Smartphone11200.01200.0
3Fone de Ouvido1200.0200.0

Ao executar a célula, observamos que a normalização da coluna "compras" foi realizada, mas as colunas "id_vendedor" e "id_cliente" foram perdidas. Para adicioná-las ao dataframe, utilizamos o parâmetro meta, especificando as chaves id_vendedor e id_cliente junto à função json_normalize.

df = pd.json_normalize(dados, record_path='compras', meta = ['id_vendedor', 'id_cliente'])
df
-produtoquantidadevalor_unitariovalor_totalid_vendedorid_cliente
0Notebook13500.03500.01011001
1Mouse250.0100.01011001
2Smartphone11200.01200.01021002
3Fone de Ouvido1200.0200.01021002

Ao executar a célula, obtemos o dataframe totalmente normalizado e manipulável.

Conclusão

Esse é o processo necessário para aplicar a normalização de JSON e construir dataframes para uso em projetos de data science. Agora, estamos prontos para avançar para os exercícios e praticar o que foi aprendido.

Desejamos boas práticas! Até logo!

Sobre o curso Python: normalizando arquivos JSON

O curso Python: normalizando arquivos JSON possui 8 minutos de vídeos, em um total de 13 atividades. Gostou? Conheça nossos outros cursos de Excel 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 Excel acessando integralmente esse e outros cursos, comece hoje!

Conheça os Planos para Empresas