【问题标题】:Deadlock in go function channelgo函数通道死锁
【发布时间】:2013-05-16 22:11:45
【问题描述】:

为什么我只是通过一个并从通道获得一个输出,但还是会出现死锁?

package main

import "fmt"
import "math/cmplx"

func max(a []complex128, base int, ans chan float64,  index chan int) {

    fmt.Printf("called for %d,%d\n",len(a),base)

    maxi_i := 0
    maxi := cmplx.Abs(a[maxi_i]);

    for i:=1 ; i< len(a) ; i++ {
        if cmplx.Abs(a[i]) > maxi {
            maxi_i = i
            maxi = cmplx.Abs(a[i])
        }
    }

    fmt.Printf("called for %d,%d and found %f %d\n",len(a),base,maxi,base+maxi_i)

    ans <- maxi
    index <- base+maxi_i
}

func main() {
    ans := make([]complex128,128)

    numberOfSlices := 4
    incr := len(ans)/numberOfSlices
    tmp_val := make([]chan float64,numberOfSlices)
    tmp_index := make([]chan int,numberOfSlices)
    for i,j := 0 , 0; i < len(ans); j++{
        fmt.Printf("From %d to %d - %d\n",i,i+incr,len(ans))
        go max(ans[i:i+incr],i,tmp_val[j],tmp_index[j])

        i = i+ incr
    }
//After Here is it stops deadlock
    maximumFreq := <- tmp_index[0]
    maximumMax := <- tmp_val[0]
    for i := 1; i < numberOfSlices; i++ {

        tmpI := <- tmp_index[i]
        tmpV := <- tmp_val[i]

        if(tmpV > maximumMax ) {
            maximumMax = tmpV
            maximumFreq = tmpI
        }
    }

    fmt.Printf("Max freq = %d",maximumFreq)

}

【问题讨论】:

    标签: parallel-processing go deadlock goroutine


    【解决方案1】:

    对于那些阅读这个问题并且可能想知道为什么他的代码失败的人,这里有一个解释。

    当他这样构建他的频道片段时:

    tmp_val := make([]chan float64,numberOfSlices)
    

    他制作了频道切片,其中每个索引都指向频道零值。通道的零值是 nil,因为通道是引用类型,并且 nil 通道会永远阻塞发送,并且由于 nil 通道中从来没有任何东西,它也会永远阻塞接收。这样你就会陷入僵局。

    当 footy 更改他的代码以单独使用构建每个通道时

    tmp_val[i] = make(chan float64)
    

    在一个循环中,他构造了非零通道,一切都很好。

    【讨论】:

      【解决方案2】:

      我弄错了chan。应该做的

      numberOfSlices := 4
      incr := len(ans)/numberOfSlices
      var tmp_val [4]chan float64
      var tmp_index [4]chan int
      
      for i := range tmp_val {
          tmp_val[i] = make(chan float64)
          tmp_index[i] = make(chan int)
      }
      
      for i,j := 0 , 0; i < len(ans); j++{
          fmt.Printf("From %d to %d [j:%d] - %d\n",i,i+incr,j,len(ans))
          go maximumFunc(ans[i:i+incr],i,tmp_val[j],tmp_index[j])
      
          i = i+ incr
      }
      

      【讨论】:

        猜你喜欢
        • 2017-06-24
        • 2018-02-02
        • 2021-12-25
        • 2020-01-24
        • 1970-01-01
        • 2017-09-06
        • 1970-01-01
        • 1970-01-01
        • 2017-10-05
        相关资源
        最近更新 更多