程式語言 - Rust - PI - Monte Carlo(Concurrency)



參考資訊:
https://tokio.rs/tokio/tutorial/spawning
https://www.rust-lang.org/learn/get-started
https://github.com/quambene/rust-concurrency
http://bzz.wallizard.com:8081/share/books/RUST/Programming%20Rust%202nd%20Edition.pdf
https://www.soroushjp.com/2015/02/07/go-concurrency-is-not-parallelism-real-world-lessons-with-monte-carlo-simulations/

產生樣板

$ cargo new hello
$ cd hello

Cargo.toml

[package]
name = "hello"
version = "0.1.0"
edition = "2021"

[dependencies]
rand = "0.8"
tokio = { version = "0.3", features = ["full"] }

src/main.rs

use rand::Rng;

fn _pi(samples : u32) -> f64 {
    let mut inside : u32 = 0;
    let mut rng = rand::thread_rng();

    for _ in 0..samples {
        let x : f64 = (rng.gen::<u32>() as f64) / f64::from(u32::MAX);
        let y : f64 = (rng.gen::<u32>() as f64) / f64::from(u32::MAX);

        if ((x * x) + (y * y)) < 1.0 {
            inside = inside + 1;
        }
    }

    if inside > 0 {
        return (f64::from(inside) / f64::from(samples)) * 4.0;
    }
    return 0.0;
}

#[tokio::main]
async fn main() {
    let mut handles = Vec::new();
    for i in 2..=8 {
        let s = u32::pow(10, i);
        let handle = tokio::spawn(async move {
            println!("Our value of Pi after {} runs: {}", s, _pi(s));
        });
        handles.push(handle);
    }
    for handle in handles {
        handle.await.unwrap();
    }
}

執行

$ cargo run
    Our value of Pi after 100 runs: 2.88
    Our value of Pi after 1000 runs: 3.144
    Our value of Pi after 10000 runs: 3.1108
    Our value of Pi after 100000 runs: 3.13984
    Our value of Pi after 1000000 runs: 3.142868
    Our value of Pi after 10000000 runs: 3.141556
    Our value of Pi after 100000000 runs: 3.14191496