A Trait Display
Parte da seção Object Oriented Programming do Journey de Rust da Coddy — lição 36 de 61.
Enquanto o Debug é ótimo para desenvolvedores que inspecionam dados, a trait Display é projetada para saída voltada para o usuário. É o que alimenta o formatador {} no println!. Diferente do Debug, o Rust não consegue derivar automaticamente o Display—você deve implementá-lo manualmente.
Para implementar Display, você precisa importar o módulo fmt e implementar o método fmt:
use std::fmt;
struct Temperature {
celsius: f64,
}
impl fmt::Display for Temperature {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{}°C", self.celsius)
}
}
O método fmt recebe um Formatter e retorna um fmt::Result. Você usa a macro write! para formatar sua saída, acessando os campos da struct através de self.
Agora você pode imprimir a struct com o formatador padrão {}:
let temp = Temperature { celsius: 23.5 };
println!("{}", temp); // 23.5°C
A principal diferença: a saída Debug mostra a estrutura dos seus dados (útil para depuração), enquanto a saída Display é polida e destinada aos usuários finais. Uma struct pode implementar ambos — use {:?} para depuração e {} para uma saída limpa.
Desafio
FácilVamos criar um sistema de exibição de produtos amigável ao usuário! Enquanto o Debug mostra a estrutura bruta dos seus dados, a trait Display permite que você crie uma saída polida e legível, perfeita para os usuários finais.
Você organizará seu código em dois arquivos:
product.rs: Defina uma struct públicaProductcom dois campos públicos:name(String) eprice(f64). Implemente a traitDisplaypara sua struct para que ela seja formatada como{name} - ${price}. Lembre-se de importarstd::fmte usar a macrowrite!dentro do seu métodofmt.main.rs: Importe seu módulo de produto e crie uma instância deProductusando as entradas fornecidas. Imprima o produto usando o formatador padrão{}para mostrar sua saída de exibição personalizada.
A trait Display exige que você implemente o método fmt manualmente — o Rust não pode derivá-lo automaticamente como o Debug. Isso lhe dá controle total sobre como seu tipo aparece para os usuários.
Sua saída deve exibir o produto em um formato limpo e amigável:
{name} - ${price}Por exemplo, com as entradas Wireless Mouse e 29.99:
Wireless Mouse - $29.99Você receberá duas entradas: o nome do produto e o preço (analise como f64).
Folha de consulta
A trait Display é projetada para saída voltada ao usuário e alimenta o formatador {} no println!. Diferente de Debug, ela deve ser implementada manualmente.
Para implementar Display, importe o módulo fmt e implemente o método fmt:
use std::fmt;
struct Temperature {
celsius: f64,
}
impl fmt::Display for Temperature {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{}°C", self.celsius)
}
}
O método fmt recebe um Formatter e retorna um fmt::Result. Use a macro write! para formatar a saída, acessando os campos da struct através de self.
Imprima a struct com o formatador {}:
let temp = Temperature { celsius: 23.5 };
println!("{}", temp); // 23.5°C
Diferença chave: Debug ({:?}) mostra a estrutura de dados para depuração, enquanto Display ({}) fornece uma saída polida para os usuários finais.
Experimente você mesmo
mod product;
use product::Product;
fn main() {
let mut name = String::new();
std::io::stdin().read_line(&mut name).expect("Failed to read line");
let name = name.trim().to_string();
let mut price_input = String::new();
std::io::stdin().read_line(&mut price_input).expect("Failed to read line");
let price: f64 = price_input.trim().parse().expect("Failed to parse price");
// TODO: Criar uma instância de Product com o name e price
// TODO: Imprimir o produto usando o formatador {}
}
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Todas as lições de Object Oriented Programming
1Métodos e Comportamento
Introdução a Blocos de ImplementaçãoO Parâmetro SelfMétodos MutáveisFunções AssociadasMúltiplos Blocos de ImplementaçãoEncadeamento de MétodosRecapitulação - Ações de Retângulo4Projeto: Pet Virtual
Definindo o PetAlimentando o Pet7Traits Padrão
A Trait DebugA Trait DisplayClone e CopyTraits de IgualdadeRecapitulação - Ponto Imprimível10Projeto: Sistema de Documentos
A Trait DrawComponente de Texto2Encapsulamento e Módulos
Fundamentos de MódulosA Palavra-chave PublicCampos PrivadosGettersSettersRecapitulação - Cofre Seguro5Genéricos
Structs GenéricasMétodos GenéricosMúltiplos Tipos GenéricosFunções GenéricasRecapitulação - Ponto de Coordenada8Traits como Restrições
Sintaxe de Restrições de TraitRestrições MúltiplasA Cláusula WhereRetornando Tipos com TraitsRecapitulação - Impressora Genérica11Padrões de Projeto em Rust
Padrão NewtypeComposiçãoA Trait DropFrom e IntoRecapitulação - Mock de Smart Pointer3Enums Avançados
Enums com DadosMétodos em EnumsCorrespondência de Variantes de DadosO Enum Option RevisitadoRecapitulação - Enum Shape6Definição de Traits
O que é uma Trait?Implementando TraitsImplementações PadrãoSobrescrevendo PadrõesTraits com ParâmetrosRecapitulação - Media Player