Skip to content

Operações com Strings no Pandas: Limpeza Vetorizada de Texto

Updated on

Colunas de texto alimentam busca, segmentação e engenharia de atributos, mas muitos pipelines ainda iteram linha a linha ou misturam None/NaN, causando filtros quebrados e código lento.

  • Problema: Caixa (maiúsculas/minúsculas), espaços em branco e correspondências parciais bagunçados tornam joins e análises pouco confiáveis.
  • Agravante: Loops em Python linha a linha são lentos, e valores ausentes inconsistentes (None vs NaN) quebram comparações.
  • Solução: Use o dtype de string do pandas com métodos vetorizados .str, controle explícito de regex e divisão/explosão segura para manter o processamento de texto rápido e previsível.

Want an AI agent that understands your pandas text cleaning and notebook context?

RunCell is a JupyterLab AI agent that can read your code, analyze DataFrames, understand notebook context, debug errors, and even generate & execute code for you. It works directly inside JupyterLab—no switching windows or copy-pasting.

👉 Try RunCell: runcell.dev (opens in a new tab)


Referência Rápida

ObjetivoMétodoExemplo
Normalizar caixa/espaços em branco.str.casefold(), .str.strip()s.str.strip().str.casefold()
Substituição literal (rápida).str.replace(..., regex=False)s.str.replace("-", " ", regex=False)
Extrair / localizar com regex.str.extract(), .str.contains()s.str.extract(r"(\d{4})")
Fazer split em colunas.str.split(expand=True)s.str.split("/", expand=True, n=2)
Fazer split em linhas.str.split().explode()df.assign(tag=df["tags"].str.split(",")).explode("tag")
Tamanho/contagens.str.len(), .str.count()s.str.count(r"\d")

Comece com um Dtype de String Adequado

import pandas as pd
 
df["title"] = df["title"].astype("string[python]")
  • Usar o dtype string (ou "string[pyarrow]" quando Arrow estiver instalado) mantém valores ausentes como <NA>, o que funciona bem com métodos .str e comparações.
  • Evite misturar objetos Python quando possível; colunas object são mais lentas e menos consistentes para operações de texto.

Padrões Centrais de Limpeza

df["clean_name"] = (
    df["name"]
      .str.strip()
      .str.replace(r"\s+", " ", regex=True)
      .str.title()
)
  • Use regex=False para substituições literais simples, evitando interpretação acidental de regex e melhorando a velocidade.
  • .str.normalize("NFKC") ajuda a unificar variantes Unicode ao comparar entradas de usuários.

Removendo ruído e aplicando caixa

df["search_key"] = df["product"].str.casefold().str.replace("-", " ", regex=False)

casefold é mais robusto que lower para comparações de texto internacionalizadas.


Filtrando e Extraindo

# Verificações exatas de prefixo/sufixo
promo_rows = df[df["code"].str.startswith("PROMO", na=False)]
 
# contains com regex e tratamento seguro de NA
has_year = df["description"].str.contains(r"\b20\d{2}\b", regex=True, na=False)
 
# Grupos de captura em colunas
df[["year", "country"]] = df["id"].str.extract(r"(?P<year>\d{4})-(?P<country>[A-Z]{2})")
  • Defina na=False ao filtrar para tratar valores ausentes como não correspondentes.
  • Grupos nomeados em extract criam colunas legíveis sem necessidade de renomear depois.

Split, Expand e Explode

# Split em múltiplas colunas
df[["city", "state"]] = df["location"].str.split(",", n=1, expand=True)
 
# Split de uma coluna tipo lista em linhas
tags = df.assign(tag=df["tags"].str.split("|"))
tags = tags.explode("tag").assign(tag=lambda t: t["tag"].str.strip())
  • Use expand=True para manter colunas alinhadas; prefira explode quando cada célula contém vários tokens que devem virar linhas.
  • Limpe os pedaços (str.strip, str.casefold) antes de joins ou agregações.

Contando e Medindo Texto

df["word_count"] = df["abstract"].str.split().str.len()
df["digit_count"] = df["code"].str.count(r"\d")
  • .str.len() respeita <NA>; os resultados são Int64 quando a entrada é dtype string.
  • Combine com fillna(0) se você precisar de inteiros “puros” para pipelines numéricos posteriores.

Dicas de Performance e Segurança

  • Prefira métodos vetorizados .str em vez de apply(lambda ...); eles são mais rápidos e cientes de NA.
  • Especifique regex=False quando você só precisar de substituições literais para evitar o custo do regex.
  • Para colunas de texto grandes, considere string[pyarrow] para reduzir memória e acelerar operações comuns (requer pyarrow instalado).
  • Normalize chaves intermediárias uma única vez (strip + casefold) e reutilize-as para joins ou deduplicação em vez de recalculá-las.

Operações vetorizadas com strings mantêm a limpeza de texto concisa e performática. Combine-as com pandas-data-cleaning para verificações de qualidade mais amplas e use com pandas-merge-join quando as chaves normalizadas estiverem prontas para joins confiáveis.