Expressões Regulares em Rust: Uma Ferramenta Poderosa para Trabalhar com Strings
Expressões regulares (regex) são uma ferramenta indispensável para pesquisar, extrair e substituir texto com base em um padrão específico. Em Rust, o trabalho com expressões regulares é implementado através da popular crate regex, que oferece alto desempenho e segurança, características da linguagem. Neste artigo, abordaremos os fundamentos do trabalho com expressões regulares em Rust usando exemplos concretos.
Instalação e Inclusão da Crate regex
Para começar, adicione a dependência ao arquivo Cargo.toml do seu projeto:
[dependencies]regex = "1"Em seguida, importe os módulos necessários no seu código:
use regex::Regex;Criação e Uso Básico de Expressões Regulares
O tipo principal para trabalhar com expressões regulares é Regex. Ele é criado usando o método Regex::new(), que recebe uma string de padrão e retorna um Result. Vamos ver um exemplo simples de busca por uma palavra em uma string:
use regex::Regex;
fn main() { let re = Regex::new(r"hello").unwrap(); let text = "hello world, hello Rust!"; // Verificando se há correspondência if re.is_match(text) { println!("Correspondência encontrada!"); } // Encontrando a primeira correspondência match re.find(text) { Some(mat) => println!("Encontrado: '{}'", mat.as_str()), None => println!("Nenhuma correspondência"), } // Encontrando todas as correspondências for mat in re.find_iter(text) { println!("Encontrado: '{}' na posição {}", mat.as_str(), mat.start()); }}Observe o uso de uma string crua (r"..."). Isso evita a necessidade de escapar barras invertidas, o que é especialmente conveniente ao trabalhar com expressões regulares.
Grupos de Captura e Extração de Dados
Grupos de captura permitem extrair partes de uma string que correspondem a partes específicas do padrão. Em Rust, os grupos são indicados por parênteses ():
use regex::Regex;
fn main() { // Extraindo uma data no formato YYYY-MM-DD let re = Regex::new(r"(\\d{4})-(\\d{2})-(\\d{2})").unwrap(); let text = "Hoje: 2024-01-15, ontem: 2024-01-14"; for cap in re.captures_iter(text) { println!("Ano: {}, Mês: {}, Dia: {}", &cap[1], &cap[2], &cap[3]); } // Extraindo endereços de email let email_re = Regex::new(r"([\\w.]+)@([\\w.]+)").unwrap(); let email_text = "Contatos: user@example.com, admin@test.org"; if let Some(caps) = email_re.captures(email_text) { println!("Usuário: {}", &caps[1]); println!("Domínio: {}", &caps[2]); }}Os grupos podem ser nomeados para melhorar a legibilidade do código:
use regex::Regex;
fn main() { let re = Regex::new(r"(?P<year>\\d{4})-(?P<month>\\d{2})-(?P<day>\\d{2})").unwrap(); let text = "2024-01-15"; if let Some(caps) = re.captures(text) { println!("Ano: {}", caps.name("year").unwrap().as_str()); println!("Mês: {}", caps.name("month").unwrap().as_str()); println!("Dia: {}", caps.name("day").unwrap().as_str()); }}Substituição de Texto Usando Expressões Regulares
A crate regex fornece métodos poderosos para substituição de texto. Vamos ver várias opções:
use regex::Regex;
fn main() { let re = Regex::new(r"\\d+").unwrap(); let text = "Eu tenho 2 gatos e 3 cachorros"; // Substituição simples de todos os dígitos por uma palavra let result = re.replace_all(text, "vários"); println!("{}", result); // "Eu tenho vários gatos e vários cachorros" // Substituição usando grupos de captura let re2 = Regex::new(r"(\\w+)@(\\w+)").unwrap(); let email = "user@example.com"; let replaced = re2.rep