[Go] Channel을 배워보자

0xDave·2022년 7월 5일

Go

목록 보기
4/10

채널은 쉽게 말해서 goroutine끼리 메세지를 주고받을 수 있는 통로 다. 나보다 더 좋은 설명으로 작성된 불곰님 글을 보면 이해가 쉬울 것이다. (그림이 진짜 잘 돼있습니다!) 아래 채널 예제를 살펴보자.

채널 생성 전


func main() {
	
	people := [2]string{"nico", "lynn"}
	for _, person := range people {
		isSexy(person)
	}
}

func isSexy(person string) bool {
	time.Sleep(time.Second * 5)
	return true
}

채널 생성 후


func main() {

	c := make(chan bool) // 채널 생성
	people := [2]string{"nico", "lynn"}
	for _, person := range people {
		isSexy(person, c) // 채널 파라미터 추가
	}
	fmt.Println(<-c) // 채널로부터 true를 받아온다
    fmt.Println(<-c) // 반복문이라 2개 받아온다
}

func isSexy(person string, c chan bool) { // 채널 파라미터 추가
	time.Sleep(time.Second * 5)
	fmt.Println(person)
	c <- true // true를 채널로 전송
}

채널을 사용하려면 일단

  1. make() 를 이용해 채널을 만들고
  2. 채널을 사용할 함수 파라미터에 채널을 추가해준다.
  3. 함수 안에 채널명 <- 전달할 메세지를 입력하고
  4. 메세지를 사용하고 싶은 곳에서 <- 기호를 이용해 메세지를 꺼내면 된다.

메세지의 타입에 따라 채널 타입을 지정해주면 끝!

🚨주의할 점


  • goroutine이 실행되고 있더라도 main() 함수가 끝나면 goroutine도 같이 끝난다.
  • 채널에서 메세지를 꺼내오려고 하는데 메세지가 없다면, 새로운 메세지가 들어올 때까지 대기상태가 된다.
  • 또한, 채널에 메세지를 보내려고 하는데 이미 메세지가 꽉 차있다면, 먼저 들어간 메세지가 나올 때까지 대기상태가 된다.

아래 예제를 보면 좀 더 이해하기 쉬운데
func pop(c chan int) {
	fmt.Println("Pop func")
	v := <-c
	fmt.Println(v)
}

func main() {
	c := make(chan int)
	go pop(c)
	c <- 10

	fmt.Println("The end")
}
//출력값
Pop func
10
The end

main() 함수가 실행되고 pop() 이 실행되는데, pop() 내부에서 채널로부터 메세지를 받으려고 한다. 그런데 채널에 아직 메세지가 없는 상태 이므로 대기상태가 되고, 다시 main() 으로 돌아가서 10을 채널에 전송하고 나서야 pop() 이 돌아가기 시작해 10을 출력한다. pop() 이 다 끝나고 main() 함수로 돌아와 The end를 출력한다.

profile
Just BUIDL :)

0개의 댓글