传递在线程之间的C中创建的TCL命令

时间:2018-03-19 19:28:19

标签: tcl

是否可以在C中创建的TCL线程(使用TCL命令创建 - Tcl_CreateObjCommand)命令之间传递(即使用Public Sub MergePDFFiles(ByVal outPutPDF As String) Dim StartPath As String = FileArray(0) ' this is a List Array declared Globally Dim document = New Document() Dim outFile = Path.Combine(outPutPDF)' The outPutPDF varable is passed from another sub this is the output path Dim writer = New PdfCopy(document, New FileStream(outFile, FileMode.Create)) Try document.Open() For Each fileName As String In FileArray Dim reader = New PdfReader(Path.Combine(StartPath, fileName)) For i As Integer = 1 To reader.NumberOfPages Dim page = writer.GetImportedPage(reader, i) writer.AddPage(page) Next i reader.Close() Next writer.Close() document.Close() Catch ex As Exception 'catch a Exception if needed Finally writer.Close() document.Close() End Try End Sub )以及如何传递?

感谢。

1 个答案:

答案 0 :(得分:3)

所有Tcl命令总是耦合到特定的解释器,解释器作为第一个参数传递给Tcl_CreateObjCommand,并且Tcl解释器严格地绑定到线程(因为Tcl实现在内部使用了很多特定于线程的变量为了减少全局锁的数量)。相反,实现通过消息在线程之间进行协调;最常见的消息是“这里是为我运行的Tcl脚本”和“这是运行该脚本的结果”,尽管还有其他的。

所以不,线程之间无法共享Tcl命令。如果你已经为它们编写了正确的代码(通常通过避免全局变量或添加适当的锁),你可以在多个线程中的多个解释器中使用相同的命令实现,但它们在技术上 相同命令,但乍看之下只是看起来一样。例如,如果在一个线程中对命令进行跟踪,则只会在该一个解释器中调用其回调,而不是从具有相同实现且具有相同名称的命令的任何其他解释器中调用。

可以在其他线程中发出委托命令,要求主线程运行命令并将结果发回给你。

package require Thread

# This procedure makes delegates; this is a little messy...
proc threadDelegateCommand {thread_id command_name} {
    # Relies on thread IDs always being “nice” words, which they are
    thread::send $thread_id [list proc $command_name args "
        thread::send [thread::id] \[list [list $command_name] {*}\$args\]
    "]
}

# A very silly example; use your code here instead
proc theExampleCommand {args} {
    puts "This is in [thread::id] and has [llength $args] arguments: [join $args ,]"
    return [tcl::mathop::+ {*}$args]
}

# Make the thread
set tid [thread::create]
puts "This is [thread::id] and $tid has just been created"

# Make the delegate for our example
threadDelegateCommand $tid theExampleCommand

# Show normal execution in the other thread
puts [thread::send $tid {format "This is %s" [thread::id]}]

# Show that our delegate can call back. IMPORTANT! Note that we're using an asynchronous
# send here to avoid a deadlock due to the callbacks involved.
thread::send -async $tid {
    after 5000
    theExampleCommand 5 4 3 2 1
} foo
vwait foo