use std::thread; use std::time::Duration; fn main() { // Create 1 thread that executes the following closure let t_handle = thread::spawn(|| { for i in 1..10 { println!("hi number {} from the spawned thread!", i); thread::sleep(Duration::from_millis(3)); } }); // Thread spawn ends and main continues executing for i in 1..5 { println!("hi number {} from the main thread!", i); thread::sleep(Duration::from_millis(1)); } t_handle.join().unwrap(); closure_move(); channel_test(); multiproducers(); mutex(); } fn closure_move() { let v = vec![1, 2, 3]; let handle = thread::spawn(move || { println!("Here's a vector: {:?}", v); }); // Imagine we dropped V here! // std::mem::drop(v); // What if thread had not yet tried accessing V? handle.join().unwrap(); } use std::sync::mpsc; fn channel_test() { let (tx,rx) = mpsc::channel(); thread::spawn(move || { let val = String::from("Hi from spawned!"); tx.send(val).unwrap(); }); let received = rx.recv().unwrap(); println!("Got message: {}", received); } fn multiproducers() { let (tx, rx) = mpsc::channel(); let tx1 = tx.clone(); thread::spawn(move || { let vals = vec![ String::from("hi"), String::from("from"), String::from("the"), String::from("thread"), ]; for val in vals { tx1.send(val).unwrap(); thread::sleep(Duration::from_secs(1)); } }); thread::spawn(move || { let vals = vec![ String::from("more"), String::from("messages"), String::from("for"), String::from("you"), ]; for val in vals { tx.send(val).unwrap(); thread::sleep(Duration::from_secs(1)); } }); for received in rx { println!("Got: {}", received); } } use std::sync::Mutex; fn mutex() { let m = Mutex::new(5); { let mut num = m.lock().unwrap(); *num = 6; } println!("m = {:?}", m); //mutex_multiple_owners_1(); //mutex_multiple_owners_Rc_2(); mutex_multiple_owners_Arc_3(); deadlock(); } //fn mutex_multiple_owners_1() { // let counter = Mutex::new(0); // let mut handles = vec![]; // // for _ in 0..10 { // let handle = thread::spawn(move || { // let mut num = counter.lock().unwrap(); // // *num += 1; // }); // handles.push(handle); // } // // for handle in handles { // handle.join().unwrap(); // } // // println!("Result: {}", *counter.lock().unwrap()); //} //use std::rc::Rc; //fn mutex_multiple_owners_Rc_2() { // // // let counter = Rc::new(Mutex::new(0)); // let mut handles = vec![]; // // for _ in 0..10 { // let counter = Rc::clone(&counter); // let handle = thread::spawn(move || { // let mut num = counter.lock().unwrap(); // // *num += 1; // }); // handles.push(handle); // } // // for handle in handles { // handle.join().unwrap(); // } // // println!("Result: {}", *counter.lock().unwrap()); //} use std::sync::Arc; fn mutex_multiple_owners_Arc_3() { let counter = Arc::new(Mutex::new(0)); let mut handles = vec![]; for _ in 0..10 { let counter = Arc::clone(&counter); let handle = thread::spawn(move || { let mut num = counter.lock().unwrap(); *num += 1; }); handles.push(handle); } for handle in handles { handle.join().unwrap(); } println!("Result: {}", *counter.lock().unwrap()); } fn deadlock() { let t1_var = Arc::new(Mutex::new(0)); let t2_var = Arc::new(Mutex::new(0)); let t1_clone = t1_var.clone(); let t2_clone = t2_var.clone(); let handle1 = thread::spawn(move || { let mut t1 = t1_var.lock().unwrap(); thread::sleep(Duration::from_secs(2)); println!("Got t1 lock, try getting t2 lock..."); let mut t2 = t2_var.lock().unwrap(); println!("This never prints..."); }); let handle2 = thread::spawn(move || { let mut t2 = t2_clone.lock().unwrap(); thread::sleep(Duration::from_secs(2)); println!("Got t2 lock, try getting t1 lock..."); let mut t1 = t1_clone.lock().unwrap(); println!("This never prints..."); }); println!("Threads Spawned..."); handle1.join().unwrap(); handle2.join().unwrap(); }