Notice
Recent Posts
Recent Comments
Link
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | ||||||
2 | 3 | 4 | 5 | 6 | 7 | 8 |
9 | 10 | 11 | 12 | 13 | 14 | 15 |
16 | 17 | 18 | 19 | 20 | 21 | 22 |
23 | 24 | 25 | 26 | 27 | 28 |
Tags
- File
- go
- Sync
- API
- c++
- mutex
- go언어
- Linux
- GO 언어
- JavaScript
- 영화
- package
- tcp
- Golang
- json
- http
- 책
- write
- C
- Python
- channel
- 리뷰
- FOR
- Callback
- window
- install
- Close
- bitcoin
- windows
- range
Archives
- Today
- Total
Code Habit
Go ) 보내기 전용 및 받기 전용 채널 사용 본문
보내기 전용 채널과 받기 전용 채널은 값의 흐름이 한 방향으로 고정된 채널이다.
- 보내기 전용( send-only ): chan <- 자료형 형식이다. c chan <- int는 int형 보내기 전용 채널 c를 뜻한다. 보내기 전용 채널은 값을 보낼 수만 있으며 값을 가져오려고 하면 컴파일 에러가 발생한다.
- 받기 전용( receive-only): <-chan 자료형 형식이다. c <- chan int는 int형 받기 전용 채널 c를 뜻한다. 받기 전용 채널은 range 키워드 또는 <- 채널 형식으로 값을 꺼낼 수만 있으며 값을 보내려고 하면 컴파일 에러가 발생한다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
|
package main
import "fmt"
func producer(c chan <- int) { // 보내기 전용 채널
for i := 0; i < 5; i++ {
c <- i
}
c <- 100 // 채널에 값을 보냄
// fmt.Println(<-c) // 채널에서 값을 꺼내면 컴파일 에러
}
func consumer(c <- chan int) { // 받기 전용 채널
for i := range c {
fmt.Println(i)
}
fmt.Println(<-c) // 채널에 값을 꺼냄
// c <- 1 // 채널에 값을 보내면 컴파일 에러
}
func main() {
c := make(chan int)
go producer(c)
go consumer(c)
fmt.Scanln()
}
// 실행 결과
0
1
2
3
4
100
|
이번에는 채널을 리턴값으로 사용해보겠다. 다음은 두 수를 더한 뒤 채널을 리턴한다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
package main
import "fmt"
func sum(a, b int) <- chan int {
out := make(chan int) // 채널 생성
go func() {
out <- a + b // 채널에 a와 b의 합을 보냄
}()
return out // 채널 변수 자체를 리턴
}
func main() {
c := sum(1, 2) // 채널을 리턴값으로 받아서 c에 대입
fmt.Println(<-c) // 3: 채널에서 값을 꺼냄
}
|
채널을리턴하려면 먼저 make 함수로 채널을 생성한다. 그리고 고루틴 안에서 채널에 값을 보낸 뒤 고루틴 바깥에서 채널을 리턴한다. 채널을 리턴값으로 받았으면 <-c처럼 값을 꺼내면 된다.
다음은 채널 매개변수와 채널 리턴값을 활용한 예제다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
|
package main
import "fmt"
func num(a, b int) <- chan int {
out := make(chan int) // int 형 채널 생성
go func() {
out <- a // 채널에 a의 값을 보냄
out <- b // 채널에 b의 값을 보냄
close(out) // 채널을 닫아서 range 키워드의 반복을 끝냄
}()
return out // 채널 변수 자체를 리턴
}
func sum(c <- chan int) <- chan int {
out := make(chan int) // int 형 채널 생성
go func() {
r := 0
for i := range c { // range를 사용하여 채널이 닫힐 때까지 값을 꺼냄
r = r + i // 꺼낸 값을 모두 더함
}
out <- r // 더한 결과를 채널에 보냄
}()
return out // 채널 변수 자체를 리턴
}
func main() {
c := num(1, 2) // 1과 2가 들어 있는 채널이 리턴됨
out := sum(c) // 채널 c를 매개변수에 넘겨서 모두 더함
// 더한 값이 들어 있는 out 채널을 리턴
fmt.Println(<-out) // 3: out 채널에서 값을 꺼냄
}
|