Newtype pattern
- Rust kursu
- İleri seviye
- Ders 64/81
- 4 dk
Newtype pattern ile trait çakışmasını çözersin.
Newtype pattern
Yetim kuralı, başka crate'lerin trait'ini başka crate'lerin türüne uygulamayı yasaklar: impl Display for Vec<String> yazılamaz. Çözüm, türü tek alanlı kendi struct'ına sarmaktır; sarmalayıcı senin türün olduğu için uygulama serbesttir:
struct Liste(Vec<String>);
impl std::fmt::Display for Liste {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
write!(f, "[{}]", self.0.join(", "))
}
}Newtype çalışma anında hiçbir maliyet getirmez; bellekte içteki türle aynıdır.
Tür güvenliği için newtype
Aynı temel türe sahip ama anlamı farklı değerler karıştırılamaz hale gelir:
struct KullaniciId(u64);
struct SiparisId(u64);
fn siparis_bul(id: SiparisId) { .. }
// siparis_bul(KullaniciId(7)); // hata: tür uyuşmuyorDoğrulama da kurucuya konabilir: Eposta::new(s) yalnızca geçerli adreslerde Some döndürürse, programın geri kalanı her Eposta'nın geçerli olduğuna güvenebilir.
Uygulama Yazdırılabilir liste
Yukarıdaki Liste newtype'ını ve Display uygulamasını yaz. Liste(vec!["elma".into(), "armut".into()]) değerini {} ile yazdır.
Başlangıç kodu
use std::fmt;
fn main() {
// buraya yaz
}Örnek çözüm
use std::fmt;
struct Liste(Vec<String>);
impl fmt::Display for Liste {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "[{}]", self.0.join(", "))
}
}
fn main() {
let l = Liste(vec!["elma".into(), "armut".into()]);
println!("{}", l);
}Beklenen çıktı
[elma, armut]
Soru ve cevaplar
Dersin sorularını cevaplarıyla birlikte inceleyebilirsin. Kendini denemek istersen dersi interaktif olarak çöz.
1 Newtype'ın dezavantajı nedir ve nasıl hafifletilir?
- Yavaştır
- Bellek harcar
- Dezavantajı yok
- İçteki türün metotları kaybolur; Deref uygulamak ya da gerekenleri yönlendirmek Doğru cevap
Açıklama: Deref her şeyi açar ve sarmalayıcının amacını zayıflatabilir; yalnızca gerekli metotları elle yönlendirmek daha kontrollüdür.
2 Sarmalayıcı
struct Liste____;
impl std::fmt::Display for Liste { .. }
struct Liste(Vec<String>);
impl std::fmt::Display for Liste { .. }
Açıklama: Tek alanlı tuple struct, newtype desenidir.
3 Uygulama ve izin
| Kavram | Anlamı |
|---|---|
impl Display for Vec<String> |
Yasak |
impl Display for Liste |
İzinli |
KullaniciId(u64) |
Tür güvenliği |
size_of::<Liste>() |
Vec ile aynı |