Dividir String em Rust (Split)

Aprenda como dividir strings em Rust usando split(), splitn(), split_whitespace(), lines() e regex. Exemplos completos e práticos.

Dividir String em Rust (Split)

Dividir strings em partes menores é uma operação fundamental em processamento de texto. Rust oferece vários métodos nativos para isso, além de suporte a expressões regulares via crate externa.

split() — dividir por delimitador

O método split() é o mais versátil. Aceita caracteres, strings e até closures como delimitador:

fn main() {
    let csv = "João,28,São Paulo,Desenvolvedor";

    // Split por caractere
    let campos: Vec<&str> = csv.split(',').collect();
    println!("Campos: {:?}", campos);
    println!("Nome: {}", campos[0]);
    println!("Idade: {}", campos[1]);

    // Split por string
    let texto = "Rust=>é=>incrível";
    let partes: Vec<&str> = texto.split("=>").collect();
    println!("Partes: {:?}", partes);

    // Split por closure (função)
    let misturado = "olá mundo;teste,outro:valor";
    let tokens: Vec<&str> = misturado
        .split(|c: char| !c.is_alphanumeric())
        .collect();
    println!("Tokens: {:?}", tokens);

    // Split por múltiplos caracteres
    let dados = "a+b-c*d/e";
    let letras: Vec<&str> = dados
        .split(&['+', '-', '*', '/'][..])
        .collect();
    println!("Letras: {:?}", letras);
}

Saída:

Campos: ["João", "28", "São Paulo", "Desenvolvedor"]
Nome: João
Idade: 28
Partes: ["Rust", "é", "incrível"]
Tokens: ["olá", "mundo", "teste", "outro", "valor"]
Letras: ["a", "b", "c", "d", "e"]

splitn() — limitar número de divisões

Use splitn() quando você precisa de um número máximo de partes:

fn main() {
    let log = "2026-02-23 INFO Servidor iniciado na porta 8080";

    // Dividir em no máximo 3 partes
    let partes: Vec<&str> = log.splitn(3, ' ').collect();
    println!("Data: {}", partes[0]);
    println!("Nível: {}", partes[1]);
    println!("Mensagem: {}", partes[2]);

    // rsplitn divide a partir do final
    let caminho = "src/modulo/arquivo.rs";
    let partes: Vec<&str> = caminho.rsplitn(2, '/').collect();
    println!("Arquivo: {}", partes[0]);
    println!("Diretório: {}", partes[1]);

    // Útil para separar chave=valor
    let config = "database_url=postgres://localhost:5432/meu_banco";
    let partes: Vec<&str> = config.splitn(2, '=').collect();
    println!("Chave: {}", partes[0]);
    println!("Valor: {}", partes[1]);
}

Saída:

Data: 2026-02-23
Nível: INFO
Mensagem: Servidor iniciado na porta 8080
Arquivo: arquivo.rs
Diretório: src/modulo
Chave: database_url
Valor: postgres://localhost:5432/meu_banco

split_whitespace() e lines()

Métodos especializados para espaços em branco e quebras de linha:

fn main() {
    // split_whitespace ignora múltiplos espaços e tabs
    let texto = "  Rust   é     incrível  ";
    let palavras: Vec<&str> = texto.split_whitespace().collect();
    println!("Palavras: {:?}", palavras);
    println!("Total: {} palavras", palavras.len());

    // lines() divide por \n ou \r\n
    let multilinhas = "Primeira linha\nSegunda linha\nTerceira linha";
    for (i, linha) in multilinhas.lines().enumerate() {
        println!("Linha {}: '{}'", i + 1, linha);
    }

    // Contando linhas não vazias
    let com_vazias = "linha 1\n\nlinha 3\n\n\nlinha 6";
    let nao_vazias: Vec<&str> = com_vazias
        .lines()
        .filter(|l| !l.is_empty())
        .collect();
    println!("Linhas não vazias: {:?}", nao_vazias);

    // Processando linhas com transformação
    let numeros = "10\n20\n30\n40";
    let soma: i32 = numeros
        .lines()
        .filter_map(|l| l.parse::<i32>().ok())
        .sum();
    println!("Soma: {}", soma);
}

Saída:

Palavras: ["Rust", "é", "incrível"]
Total: 3 palavras
Linha 1: 'Primeira linha'
Linha 2: 'Segunda linha'
Linha 3: 'Terceira linha'
Linhas não vazias: ["linha 1", "linha 3", "linha 6"]
Soma: 100

Split com regex

Para padrões mais complexos, use a crate regex:

Cargo.toml:

[dependencies]
regex = "1"
use regex::Regex;

fn main() {
    // Dividir por um ou mais espaços/pontuação
    let re = Regex::new(r"[\s,;.!?]+").unwrap();
    let texto = "Olá, mundo! Como vai? Tudo bem; obrigado.";
    let palavras: Vec<&str> = re.split(texto).collect();
    println!("Palavras: {:?}", palavras);

    // Dividir por padrão numérico
    let re = Regex::new(r"\d+").unwrap();
    let misturado = "abc123def456ghi789";
    let partes: Vec<&str> = re.split(misturado).collect();
    println!("Partes texto: {:?}", partes);

    // Capturar os delimitadores também
    let re = Regex::new(r"(\d+)").unwrap();
    let resultado: Vec<&str> = re.find_iter(misturado)
        .map(|m| m.as_str())
        .collect();
    println!("Números encontrados: {:?}", resultado);

    // Split com limite usando regex
    let re = Regex::new(r"\s*,\s*").unwrap();
    let csv = "item1 , item2 , item3 , item4 , item5";
    let primeiros: Vec<&str> = re.splitn(csv, 3).collect();
    println!("Primeiros 3: {:?}", primeiros);
}

Saída:

Palavras: ["Olá", "mundo", "Como", "vai", "Tudo", "bem", "obrigado", ""]
Partes texto: ["abc", "def", "ghi", ""]
Números encontrados: ["123", "456", "789"]
Primeiros 3: ["item1", "item2", "item3 , item4 , item5"]

Comparação dos métodos

MétodoQuando usar
split(char)Delimitador simples (vírgula, ponto, etc.)
split(&str)Delimitador de múltiplos caracteres
splitn(n, pat)Limitar número de partes
split_whitespace()Separar palavras (ignora espaços múltiplos)
lines()Separar por quebra de linha
Regex::split()Padrões complexos

Veja também