Fácil Rust

Função com lifetime explícito

Enunciado

Escreva uma função melhor<'a>(x: &'a str, y: &'a str) -> &'a str que retorna a string mais longa. Se tiverem o mesmo tamanho, retorne x. No main, chame a função com duas strings literais e imprima o resultado.

Requisitos

  • A função deve ter o parâmetro de lifetime 'a explícito.
  • Deve retornar a string mais longa ou x em caso de empate.
  • O main deve chamar a função e imprimir o resultado.

Código inicial

fn melhor<'a>(x: &'a str, y: &'a str) -> &'a str {
    // implemente
}

fn main() {
    // chame e imprima
}

Saída esperada

Mais longa: rust
Ver dica

Use if x.len() >= y.len() { x } else { y }.

Mostrar solução
// Função que retorna a string mais longa, com lifetime explícito.
fn melhor<'a>(x: &'a str, y: &'a str) -> &'a str {
    if x.len() >= y.len() { x } else { y }
}

fn main() {
    let a = "rust";
    let b = "go";
    println!("Mais longa: {}", melhor(a, b));
}

Passo a passo

  1. Declaramos fn melhor<'a>(x: &'a str, y: &'a str) -> &'a str. O 'a é um parâmetro de lifetime genérico que liga as duas entradas e a saída.
  2. Dentro da função, comparamos os comprimentos com x.len() >= y.len().
  3. Se x for maior ou igual, retornamos x; caso contrário, y.
  4. No main, criamos duas variáveis &str e chamamos melhor(a, b).
  5. O compilador verifica que o retorno não vive mais que a e b, o que é verdade.
  6. Imprimimos o resultado com println!.

Por que funciona

O lifetime 'a garante que a referência retornada é válida enquanto ambas as entradas forem válidas. Como as strings literais têm lifetime 'static, o retorno também pode ser usado sem problemas. O compilador não permite retornar uma referência a uma variável local que morre no fim da função.

Erros comuns

  • Omitir o lifetime e escrever fn melhor(x: &str, y: &str) -> &str. O compilador não consegue inferir qual entrada o retorno segue; erro missing lifetime specifier.
  • Retornar &String em vez de &str: o tipo precisa ser consistente.
  • Usar x.len() > y.len() sem tratar empate, contrariando o enunciado.

Outra forma de resolver

Você pode usar std::cmp::max_by_key com uma closure, mas precisa de lifetimes explícitos do mesmo jeito:

fn melhor<'a>(x: &'a str, y: &'a str) -> &'a str {
    std::cmp::max_by_key(x, y, |s| s.len())
}

Essa forma é mais declarativa, porém menos direta para iniciantes.

Saída esperada

Mais longa: rust