为什么在线程中运行时某些语句无法执行?

时间:2014-12-28 14:48:18

标签: multithreading rust

我无法理解this code sample的程序行为:

use std::comm;
use std::thread::Thread;

static NTHREADS: uint = 3;

fn main() {
    let (tx, rx): (Sender<uint>, Receiver<uint>) = comm::channel();

    for id in range(0, NTHREADS) {
        let thread_tx = tx.clone();

        Thread::spawn(move || {
            thread_tx.send(id);
            println!("thread {} finished", id);
        }).detach();
    }

    let mut ids = Vec::with_capacity(NTHREADS);
    for _ in range(0, NTHREADS) {
        ids.push(rx.recv());
    }

    println!("{}", ids);
}

具体来说,我不明白为什么有些任务在分离时无法到达这一行:

println!("task {} finished", id);

但不是在与父母(主要)加入时。

另外,为什么只有连接的任务以预定义的顺序执行?

2 个答案:

答案 0 :(得分:1)

此代码不会加入任务但会将其分离。这意味着任务独立于主线程(分离它的那个)

然后为每项任务选择两个选项:

  • 在println执行之前完成:然后你通过print
  • 在代码中看到它
  • 它没有完成,然后你提到的println执行而不等待它

如果您加入则表示&#34;我必须等待此任务继续进行&#34;。因此,所有任务都在执行行之前执行。

没有预定义的顺序,这使得多线程代码难以调试: - )

答案 1 :(得分:1)

您需要多次运行代码,因为无法保证线程的执行顺序。我也不知道允许在线评估的并发处理器数量是多少,因此您可能在单核计算机上运行它。我在我的多核笔记本电脑上运行了几次,得到了以下输出:

task 0 finished
task 1 finished
task 2 finished
[0, 1, 2]

task 1 finished
task 0 finished
task 2 finished
[0, 1, 2]

task 0 finished
task 1 finished
[0, 1, 2]
task 2 finished

线程的一个重要考虑因素是程序在主线程完成时完成 。在这种情况下,需要考虑4个线程:主线程和3个任务线程。主线程将在收到3条消息并打印出来后完成。其余的线程正在做什么并不重要!

当您join来自主线程的线程时,您告诉主线程要等到工作线程退出。这意味着每个线程都可以在程序退出之前执行println!