Beginners Cheatsheet
Traits
Display
Wie lassen sich Structs als String darstellen?
- Python
def __str__()
- Java
public String toString()
- Rust
trait Display
#![allow(unused)] fn main() { pub trait Display { fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error>; } }
Beispiel:
#![allow(unused)] fn main() { struct ID(u32); impl Display for ID { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { write!(f, "{}", self.0) } } #[test] fn test_display() { let id = ID(123); let s = format!("{id}"); assert_eq!(s, "ID(123)"); assert_eq!(id.to_string(), "ID(123)"); } }
From & Into
Wie lassen sich Typen value-to-value konvertieren?
- Java
constructor overloading
- Rust
trait From
#![allow(unused)] fn main() { pub trait From<T>: Sized { fn from(value: T) -> Self; } }
Beispiel:
#![allow(unused)] fn main() { struct ID(u32); impl From<u16> for ID { fn from(value: u16) -> Self { Self(value as u32) } } #[test] fn test_from() { let id = ID::from(123); assert_eq!(id.0, ID(123).0); let id: ID = 123.into(); assert_eq!(id.0, ID(123).0); } }
From
implementiert auch den Into
-Trait mit, dieser ermoeglicht den .into()
-Call
From
darf nicht fehlschlagen, dafuer existiert der TryFrom
-Trait,
z. B. kann man diesen gut fuer Konvertierung von Strings in eigene Typen verwenden,
um bei Fehlerhaften Strings ein Result zurueck zu geben.
Deref
#![allow(unused)] fn main() { pub trait Deref { // Ergebnis-Typ nach dereferenzierung type Target: ?Sized; fn deref(&self) -> &Self::Target; } #[test] fn test_deref() { let id = ID(123); assert_eq!(123, *id); } }
Beispiel:
#![allow(unused)] fn main() { struct ID(u32); impl<T> Deref for DerefExample<T> { type Target = T; fn deref(&self) -> &Self::Target { &self.value } } }
Default
Wie kann man einem Typen default Werte geben?
- Python
__init__(self, id=123, username="foo")
- Rust
trait Default
#![allow(unused)] fn main() { pub trait Default: Sized { // Required method fn default() -> Self; } }
Beispiel:
#![allow(unused)] fn main() { struct ID(u32); impl Default for ID { fn default() -> Self { Self(0) } } }
Beispiel mit Enum:
#![allow(unused)] fn main() { enum Command { Help, Run, Build, } impl Default for Command { fn default() -> Self { Command::Help } } }
Iterator
Wie mache ich eigene Typen iterierbar?
- Python
def __next__(self)
- Java
implements Iterable<T>
- Rust
trait Iterator
Beispiel
#![allow(unused)] fn main() { struct IDS(Vec<u32>); impl Iterator for IDS { type Item = u32; fn next(&mut self) -> Option<Self::Item> { self.0.pop() } } #[test] fn test_iterator() { let mut ids = IDS(vec![1, 2, 3]); assert_eq!(ids.next(), Some(1)); assert_eq!(ids.next(), Some(2)); assert_eq!(ids.next(), Some(3)); } }