当前位置: 首页 > 知识库问答 >
问题:

等效二叉树练习,实现"并发"

融修平
2023-03-14

我正在解围棋中的练习,等价的二叉树。此练习需要实现一个Walk函数,该函数将遍历一棵树,并将所有值有序地从树发送到通道。

演习声明指出:

...我们将使用Go的并发和通道编写一个简单的解决方案。

阅读这一行,我认为实现Walk是一个挑战,它为每个左/右子树启动一个goroutine,并使Walk比非并发版本运行得更快(关于时间复杂度)。让我用代码更详细地解释一下。

这是我早期的行走代码:

func Walk(t *tree.Tree, ch chan int) {
    defer close(ch)
    if t == nil { return }
    
    lch, rch := make(chan int), make(chan int)
    go Walk(t.Left, lch)
    for v := range lch { ch <- v }

    ch <- t.Value

    go Walk(t.Right, rch)
    for v := range rch { ch <- v }

    return
}

它当然使用goroutines,但实际上与没有goroutines的遍历没有什么不同,因为v:=range lch{...}延迟go Walker(t.右,rch)直到它结束。

向上移动没有任何区别go Walker(t.右,rch)

func Walk(t *tree.Tree, ch chan int) {
    defer close(ch)
    if t == nil { return }
    
    lch, rch := make(chan int), make(chan int)
    go Walk(t.Left, lch)
    go Walk(t.Right, rch)

    for v := range lch { ch <- v }
    ch <- t.Value
    for v := range rch { ch <- v }
}

走(t.左,lch)沿着整个左子树(以蓝色为根)行走,并且立即接收从lch发送的值。

走(t.右,rch)试图走,但被阻止作为ch

我的问题是:如何实现Walk,使goroutines(对应于左或右)避免被ch阻塞


共有1个答案

牛凌
2023-03-14

右子树中的值需要一个缓冲区(例如缓冲通道),因为它们必须持续到这些值之前(

为大小未知的子树准备缓冲区有几个含义

  • 如果使用了缓冲通道,make(chan int,N),则选择N至关重要。如果N恰好对于子树来说太小,则子树的goroutine会很快阻塞。如果内存太大,则会不必要地浪费内存

在我看来,这类问题没有简单而通用的解决方案,“遍历一个随机的、未知的树,并发被挤出”。

 类似资料:
  • 问题内容: 我正在尝试解决等效的二叉树演习。这是我所做的; 但是,我无法找出如何发信号通知树中是否还剩下任何元素。我无法使用on,因为它会使通道在所有值发送之前关闭(因为递归。)有人可以在这里帮我吗? 问题答案: 如果Walk函数本身不递归,则可以使用close()。即步行将做: 其中walkRecurse或多或少是您当前的Walk功能,但是在walkRecurse上递归。(或者您将Walk重写为

  • 我正在努力解决等价的二叉树问题。这就是我所做的; 然而,如果树中没有任何元素,我无法找到如何发出信号。我不能在上使用,因为它会在发送所有值之前关闭通道(因为递归)有人能帮我一下吗?

  • 二叉树是最简单的树形数据结构,虽然它在许多语言中被哈希表取代,但仍旧对于一些应用很实用。二叉树的各种变体可用于一些非常实用东西,比如数据库的索引、搜索算法结构、以及图像处理。 我把我的二叉树叫做BSTree,描述它的最佳方法就是它是另一种Hashmap形式的键值对储存容器。它们的差异在于,哈希表为键计算哈希值来寻找位置,而二叉树将键与树中的节点进行对比,之后深入树中找到储存它的最佳位置,基于它与其

  • 在本练习中,我将让你将数据结构的中文描述翻译成工作代码。你已经知道如何使用“大师复制”方法,分析算法或数据结构的代码。你还可以了解如何阅读算法的伪代码描述。现在你将结合二者,并学习如何拆分一个相当松散的二进制搜索树的英文描述。 我打算马上开始,并提醒你,当你做这个练习的时候,不要访问维基百科页面。维基百科的二进制搜索树描述拥有可以工作的 Python 代码,因此它会使此练习失败。如果你卡住了,那么

  • (https://github.com/golang/tour/blob/master/solutions/binarytrees_quit.go)练习:等价二叉树假设我们有两个简单的等价二叉树“1 3 5”和“2 3 5”。当两个goroutine“Walk”同时在叶“1”和“2”处行走时, 函数中的条件相同将为真 会跑。 通道“quit”将接收消息,并执行select语句的第二种情况。然后它将

  • 我正在学习,在本教程中,可以使用并发和通道来完成这个练习:解决方案。 我试图通过解决这个问题。我能想到的解决方案是使用临时数据结构来存储顺序遍历这两棵树的结果,然后进行比较。 例如,我使用存储顺序遍历的结果,然后进行比较(注意,我们正在比较排序的二叉树): 测试用例: 我想知道有没有其他更好的方法通过解决这个问题?