Created
June 23, 2020 11:45
-
-
Save haraldh/47789f21923b54284fdac5fcc11b9ef6 to your computer and use it in GitHub Desktop.
use &mut T, Box<T> and &mut dyn T in one function
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use std::ops::DerefMut; | |
use std::thread::sleep; | |
use std::time::Duration; | |
trait DigitalInput { | |
fn set_state(&mut self, _new_state: bool); | |
} | |
trait Mutable<T: ?Sized> { | |
fn ref_mut(&mut self) -> &mut T; | |
} | |
impl<'a, T: ?Sized> Mutable<T> for &'a mut T { | |
fn ref_mut(&mut self) -> &'_ mut T { | |
self | |
} | |
} | |
impl<T: ?Sized> Mutable<T> for Box<T> { | |
fn ref_mut(&mut self) -> &'_ mut T { | |
self.deref_mut() | |
} | |
} | |
fn flash_periodically<L: Mutable<P>, P: DigitalInput + ?Sized>(mut lamp: L, interval: Duration) { | |
let mut current_state = false; | |
loop { | |
lamp.ref_mut().set_state(current_state); | |
current_state = !current_state; | |
sleep(interval); | |
} | |
} | |
struct Pin; | |
impl DigitalInput for Pin { | |
fn set_state(&mut self, _new_state: bool) { | |
unimplemented!() | |
} | |
} | |
fn main() { | |
let pin: &mut Pin = &mut Pin; | |
flash_periodically(pin, Duration::from_millis(100)); | |
let pin: Box<dyn DigitalInput> = Box::new(Pin); | |
flash_periodically(pin, Duration::from_millis(100)); | |
let pin: &mut dyn DigitalInput = &mut Pin; | |
flash_periodically(pin, Duration::from_millis(100)); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment