Tcl Thread:如何在线程中访问全局变量

时间:2015-02-20 05:31:40

标签: multithreading tcl

我有一个名为“startMyProc {num}”的proc。我希望这个proc由两个不同的线程调用,并等待两个线程完成。我尝试了给出的解决方案。我想访问startMyProc中的全局变量并调用另一个proc“startMyAnotherProc {num}”。怎么办呢?

package require Thread


global myVar

set myVar false

set id1 [thread::create -joinable {
    source sample.tcl
    thread::wait
    }]
set id2 [thread::create -joinable {
    source sample.tcl
    thread::wait
    }]

set num 1
thread::send -async $id1 [list startMyProc $num]
set num 2
thread::send -async $id2 [list startMyProc $num]

thread::join $id1
thread::join $id2

My sample.tcl looks like this,

proc startMyProc { num } {
    global myVar
    puts $myVar
    puts "Opening $num"
    after 2000
    puts "Opening $num"
    after 2000
    puts "Opening $num"
    after 2000
    startMyAnotherProc $myVar
    return
}

proc startMyAnotherProc { num } {
    puts "Opening Another Proc: $num"
    after 2000
    puts "Opening Another Proc: $num"
    after 2000
    return
}

1 个答案:

答案 0 :(得分:3)

每个主题都有自己的完整解释器,与程序中的所有其他解释器隔离(thread包的命令除外)。在所有线程中获取过程的最简单,最直接的方法是将其放在脚本文件中,然后将source作为线程启动脚本的一部分:

set t1 [thread::create -joinable {
    source myProcedures.tcl
    startMyProc $num
}]
set t2 [thread::create -joinable {
    source myProcedures.tcl
    startMyProc $num
}]

但是你会遇到另一个问题。变量不共享。这意味着您不会让$num结束。你应该真的让脚本启动,然后在最后做thread::wait。然后,您可以thread::send他们的工作(并在构建脚本时获得替换)。

set t1 [thread::create -joinable {
    source myProcedures.tcl
    thread::wait
}]
set t2 [thread::create -joinable {
    source myProcedures.tcl
    thread::wait
}]
thread::send -async $t1 [list startMyProc $num]
thread::send -async $t2 [list startMyProc $num]

但是,如果您真的在考虑向工作线程发送任务,那么您应该查看线程池(tpool)支持;它的很多更容易扩展。

# Make the thread pool
set pool [tpool::create -initcmd {
    source myProcedures.tcl
}]

# Sent the work into the pool as distinct jobs
set job1 [tpool::post $pool [list startMyProc $num]]
set job2 [tpool::post $pool [list startMyProc $num]]

# Wait for all the jobs in the pool to finish
set waitingfor [list $job1 $job2]
while {[llength $waitingfor] > 0} {
    tpool::wait $pool $waitingfor waitingfor
}

# Get results now with tpool::get

# Dispose of the pool
tpool::release $pool