首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >用两个返回的args为func创建chan

用两个返回的args为func创建chan
EN

Stack Overflow用户
提问于 2015-01-06 08:46:49
回答 2查看 1.2K关注 0票数 4

为函数boolInt创建通道而不重新定义它是可行的吗?

代码语言:javascript
复制
package main

func boolInt() (bool, int) {
    return false, 1
}

func main() {
    chanBool := make(chan bool)
    chanInt := make(chan int)
    go func() {
        // chanBool <- boolInt() // error: multiple-value boolInt() in single-value context
        chanBool, chanInt <- boolInt() //  syntax error: unexpected semicolon or newline, expecting := or = or comma
    }()

}

当我尝试在单个值上下文chanBool <- boolInt()中使用它时,我会得到一个错误:multiple-value boolInt() in single-value context

在2-值上下文中:chanBool, chanInt <- boolInt() got:syntax error: unexpected semicolon or newline, expecting := or = or comma

游乐场

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-01-06 08:53:24

使用2个不同的通道

您希望将值发送到两个不同的通道。向通道发送值不是赋值,因此不能一步一步地在两个通道上发送。

首先存储boolInt()返回的值,然后将值发送到两个通道,如下所示:

代码语言:javascript
复制
go func() {
    b, i := boolInt()
    chanBool <- b
    chanInt <- i
}()

测试它:

代码语言:javascript
复制
go func() {
    b, i := boolInt()
    chanBool <- b
    chanInt <- i
}()

fmt.Println("Received bool:", <-chanBool)
fmt.Println("Received int:", <-chanInt)

输出:

代码语言:javascript
复制
Received bool: false
Received int: 1

备注:首先必须从chanBool接收到的,因为您创建了未缓冲的通道,而且在我们首先发送给chanBool的示例中,该通道会阻塞,直到重新发送发送的值,然后才会继续向chanInt发送值。首先尝试从chanInt接收将导致死锁("fatal error: all goroutines are asleep - deadlock!")。

只使用一个通道的解决方案

如果要在通道上发送多个值,可以为这些值创建包装器struct

代码语言:javascript
复制
type MyStruct struct {
    b bool
    i int
}

并使用它:

代码语言:javascript
复制
ch := make(chan MyStruct)
go func() {
    b, i := boolInt()
    ch <- MyStruct{b, i}
}()

fmt.Println("Received value:", <-ch)

输出:

代码语言:javascript
复制
Received value: {false 1}

注意:您也可以使用[]interface{}片作为包装器,但是结构为其字段提供了更清晰的方法和类型安全性。

注释2:如果boolInt()函数本身返回MyStruct值,将使事情变得更加简单和清晰:

代码语言:javascript
复制
func boolInt() MyStruct {
    return MyStruct{false, 1}
}

在这种情况下,代码将非常简单:

代码语言:javascript
复制
ch := make(chan MyStruct)
go func() {
    ch <- boolInt()
}()

备选1通道解决方案

另一个选项是使通道类型为interface{},这样它就可以接收任意类型的值,并且只需在它上发送/接收多个值:

代码语言:javascript
复制
ch := make(chan interface{})
go func() {
    b, i := boolInt()
    ch <- b
    ch <- i
}()

fmt.Println("Received values:", <-ch, <-ch)

输出:

代码语言:javascript
复制
Received values: false 1
票数 7
EN

Stack Overflow用户

发布于 2015-01-06 09:29:54

如果要在通道上一起发送两个值,一个选项是使用结构将两个值打包在一起。例如:

代码语言:javascript
复制
type BoolPlusInt struct {
    B bool
    I int
}

然后,您可以创建此类型的值,保存这两个值,然后再将其发送到通道中。例如:

代码语言:javascript
复制
c := make(chan BoolPlusInt)
go func() {
    var v BoolPlusInt
    v.B, v.I = boolInt()
    c <- v
}()

如果您在信道上发送或接收多个goroutines,则此解决方案可能更可取。由于这两个值是打包在一起的,所以您不需要担心一个地方的错误会导致两个通道不同步。

您可以在这里试验这个建议:Apg4ciFI

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/27795036

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档