Regex - Como extrair sentenças usando condições (maiúscula e minúsculas)

Prezadxs, olá!

Estou com um problema na extração de sentenças de uma coluna. Basicamente é uma extração de tabela em formato de texto, ai as colunas vêm todas bagunçadas e não estou conseguindo resolver o problema para duas delas: região e município.

Essas duas colunas ficaram unidas em apenas uma, da seguinte forma: Região MUNICÍPIO. Com o nome da região contendo a primeira letra maiúscula e o restante minúsculo, o município em caixa alta.

Tentei algumas coisas com regex, trabalhando com "[a-z]" e "[A-Z]" porém não consegui capturar muito bem, sempre faltava algo. O que fiz pra resolver foi usar a função stringr::word para extrair as sentenças de acordo com a ordem delas.

Contudo, essa resolução não se mostrou factível para ser usada na coluna da tabela, pois tenho situações onde a primeira palavra por exemplo já é o MUNICÍPIO, por não ter região, e outras onde a ordem muda ou tem apenas a região. Acredito que a melhor forma seja alguma coisa com regex.

Dúvida: alguém poderia auxiliar na construção dessa regex para separar essas informações de região e município, por gentileza?

Deixo em seguida um exemplo de uma situação da tabela (que funciona, porém não é reproduzível para a coluna inteira, pois gera muitos erros).

# instalar e carregar pacote
# install.packages("stringr")
# library(stringr)

# string de exemplo
str_texto <- "Médio-Norte SÃO JOSÉ DO RIO CLARO"

# extrair a primeira palavra (primeira letra maiúscula e restante minúsculo)
regiao <- stringr::word(str_texto)
regiao
#> [1] "Médio-Norte"

# extrair o município (em caixa alta)
municipio <- stringr::word(str_texto, start = 2, end =6)
municipio
#> [1] "SÃO JOSÉ DO RIO CLARO"

Created on 2021-07-18 by the reprex package (v2.0.0)

Agradeço qualquer ajuda!

Abraços.

Olá!

Obrigado pelo exemplo reprodutível. Minha solução usa duas ranges de regex: as letras maiúsculas normais e as letras maiúsculas com acentos. Para fazer ranges personalizadas eu uso o graphemica.com.

library(magrittr)

# Exemplo
str_texto <- "Médio-Norte SÃO JOSÉ DO RIO CLARO"

# Municipio
municipio <- str_texto %>% 
  stringr::str_extract("[A-Z\u00C0-\u00DD ]+$") %>% 
  stringr::str_squish()

# Região
regiao <- str_texto %>% 
  stringr::str_remove(municipio) %>% 
  stringr::str_squish()

# Parece funcionar
municipio
#> [1] "SÃO JOSÉ DO RIO CLARO"
regiao
#> [1] "Médio-Norte"

Created on 2021-07-19 by the reprex package (v2.0.0)

1 Curtida

Caio, muito obrigado pela resolução!
Sua ajuda é sempre certeira, ainda mais se tratando de regex.
A solução serviu perfeitamente para meu problema. Só fiquei com algumas dúvidas em relação ao código, dúvidas de aluno mesmo:

  1. O uso do range personalizado, se fez necessário por conta das letras maiúsculas com acento? Ou existiria outra forma de realizar isso?
  2. Quando sei que é necessário o uso desses ranges personalizados?
  3. Estou sofrendo ainda com regex, tem alguma recomendação de leitura que ajude nesse processo de aprendizado? Tenho por mania consultar o material do curso R para Ciência de Dados 2, só que as situações na prática são sempre mais complexas haha.

Muitíssimo obrigado pela ajuda!

Abraços.

  1. Isso mesmo. Existem alguns ranges que ensinamos nos cursos (A-Z, a-z e 0-9), mas na verdade podemos fazer qualquer range utilizando os código Unicode dos caracteres.
  2. O range personalizado só é necessário quando você precisar pegar caracteres que não estão incluídos nos ranges “padrões” que listei acima.
  3. Eu costumo explorar o regex101.com, com a ressalva de que nele não é necessário usar barras duplas (\\) que costumamos usar no R.
1 Curtida

Obrigado pelos esclarecimentos, Caio!

1 Curtida