한 눈에 끝내는 고랭 기초
    • 01
      시작하기에 앞서
    • 강의대상
      Go란?
      실습 환경 구축 - 구름IDE
      Hello goorm! 출력해보기
    • 02
      변수와 상수
    • 콘솔 출력 함수의 기본
      변수의 선언과 초기화
      상수의 선언과 초기화
      간단한 덧셈
      잘못된 신상정보
    • 03
      연산자
    • 연산자 종류
      연산자 우선순위
      콘솔 입력 함수의 기본
      간단한 덧셈과 곱셈
      몫과 나머지
    • 04
      자료형
    • 자료형의 종류와 특징
      문자열의 표현
      자료형의 변환
      강제 형 변환
    • 05
      콘솔 출력과 입력 함수
    • 콘솔 출력 함수(Print)
      콘솔 입력 함수(Scan)
      정돈된 표
      신상정보 입력과 출력
    • 06
      반복문 - for
    • 오로지 for
      구구단
      빛나는 이등변삼각형
    • 07
      조건문 - if/else
    • 조건에 따른 실행과 흐름 분기
      7과 9의 배수
      두 수의 차
    • 08
      분기문 - switch
    • swich문에 의한 선택적 실행
      안좋은 계산기
    • 09
      제어문
    • break, continue, goto문
      구구단2
      두 수를 더하면 99
    • 10
      컬렉션
    • 배열(Array)
      슬라이스(Slice)
      맵(Map)
      역행렬
      가장 긴 이름
      중간고사 평균 점수
    • 11
      함수
    • Go언어에서의 함수
      전역변수와 지역변수
      매개변수
      반환값(리턴값)
      익명 함수
      오름차순 정렬
      아이패드를 사주는 조건
      역학적 에너지
    • 12
      클로저
    • 외부 변수 접근 : 클로저
      동전 정리
    • 13
      구조체와 메소드
    • 구조체
      메소드
      성적 저장 프로그램
      역학적 에너지2
    • 14
      인터페이스(interface)
    • 메소드의 집합 인터페이스
      직육면체와 원기둥
    • 15
      defer와 panic()
    • 지연 처리 defer
      종료하는 panic(), 복구하는 recover()
      엘리베이터
      중간고사 평균 점수2
    • 16
      에러 처리
    • 에러 처리의 기본
      에러 출력 및 처리
      중간고사 평균 점수3
    • 17
      고루틴(Goroutine)
    • 비동기 프로세스의 기본
      고루틴의 활용
      고루틴 실습
    • 18
      채널(Channel)
    • 고루틴의 데이터 통로 : 채널
      비동기 채널과 버퍼
      동기 채널
      채널 닫기
      송신 전용, 수신 전용 채널
      채널 select문
      고루틴 실습2
      메시지 전송
      동기 채널 실습
      비동기 채널 실습
    • 19
      패키지(package)
    • 패키지의 개념
    • 20
      실전 프로젝트 - 마일리지 상점
    • 프로젝트를 시작하기 앞서
      실습모드에서 실습
      마일리지 상점의 주요 기능
      필수 구조체와 매인 메뉴
      잔여 수량, 잔여 포인트 구현
    • 21
      실전 프로젝트 - 주문하기, 장바구니 담기
    • 구매 구현(1)
      구매 구현(2)
      장바구니에 담기
      장바구니 확인(1)
      장바구니 확인(2)
    • 22
      실전 프로젝트 - 고루틴으로 배송하기
    • 배송 상태 확인(1)
      배송 상태 확인(2)
      배송 상태 확인(3)
      최종 코드
    고루틴의 데이터 통로 : 채널
    18 채널(Channel)
    고루틴의 데이터 통로 : 채널

    이 과목은 Go언어를 활용한 '프로젝트'를 만드는 것이 목적이 아니라 용법을 배우는 것이 목적인 과목이기 때문에 기본적인 예제 코드와 알고리즘 성격이 강한 실습 코드를 다뤘습니다. 그런데 사실 강의 후반부에 시작한 'defer와 panic()' 챕터부터의 학습 내용은  실제 프로젝트에 적용했을 때 그 편리함과 장점을 실감할 수 있습니다. 에러 처리도 굉장히 중요한 용법이지만 이전 강의에서 '고루틴'을 학습하고 Go언어의 장점인 비동기성 프로그래밍을 직접 느껴봤습니다. 고루틴을 사용하면 비동기적으로 여러개의 함수를 실행할 수 있고 이를 활용해 각 데이터를 동시에 서버에 전송할 수 있는 기능을 가지고 있는 것입니다.

    그런데 고루틴을 사용할 때 우리가 이전 강의에서 생각해보지 못한 문제가 발생할 수 있습니다. 우리가 알고있는 함수의 기본 형식 예시를 살펴보고 어떤 문제가 발생할 수 있을지 생각해봅니다.

    go
    실행 결과를 확인해보세요!
    default

    위 예시는 쉬운 기본 코드입니다. 익명함수 클로저에서 두 수를 더하는 연산을 하고 result에 결괏값을 저장합니다. 그리고 printResult() 함수에 result가 전해지고 출력됩니다. 동기적인 함수들의 실행 흐름은 전혀 문제될 것이 없습니다. 위에서부터 순서대로 함수가 호출되고 종료되기 때문에 자연스러운 흐름을 하기 때문입니다.

    그런데 만약 익명 함수를 고루틴에서 호출하면 어떻게 될까요? 익명함수에서 연산한 결괏값이 printResult() 함수에 전달되기도 전에 프로그램이 종료될 것입니다. 이 예시는 두 함수만이 값을 주고받지만 만약, 프로그램이 커서 엄청나게 많은 고루틴이 생성되고 값을 주고받는다면 걷잡을 수 없이 문제가 커지게 됩니다. 고루틴은 비동기적으로 실행되기 때문에 다른 고루틴에서 실행되는 함수의 종료 여부와는 상관없이 진행됩니다. 그래서 만약 값을 연산하고 반환하는 고루틴이 먼저 종료된다면 문제가 발생하게 됩니다. 그래서 고루틴끼리 서로 값을 주고받는 통로가 필요합니다. 그것이 바로 이번 강의에서 배우는 채널(Channel)입니다. 이는 고루틴을 사용하는데 있어 굉장히 중요한 역할을 합니다.


    아래 코드를 바로 실행해보세요.

    go
    실행 결과를 확인해보세요!
    default

    지난 강의에서 모든 고루틴이 종료되기 전까지 대기하는 방법으로

    1. 주먹구구식으로 main() 함수 마지막에 fmt.Scanln() 함수를 쓰는 방법
    2. WaitGroup 사용으로 모든 고루틴 종료 대기

    를 학습했습니다. 그런데 말 그대로 이는 고루틴이 모두 종료되는 것을 기다리게 하는 용법일 뿐이지 고루틴 사이에 흐름을 제어하지는 않습니다. 채널은 고루틴 사이에서 값을 주고받는 통로 역할을 하고, 송/수신자가 서로를 기다리는 속성때문에 고루틴의 흐름을 제어합니다. 그리고 채널의 데이터를 주고 받을때까지 해당 고루틴을 종료하지 않아 별도의 lock을 하지 않고도 데이터를 동기화 하는데 사용합니다.

    채널은

    • "make(chan 데이터타입)" 형식으로 생성합니다.
    • 채널의 데이터 송/수신은 '<-' 연산자를 이용합니다.
    • 체널에 값을 보낼 때는 채널 <- 데이터, 채널에서 값을 받을 때는 <- 채널 입니다. 값을 받을 때는 :=이나 =을 이용해 변수에 바로 값을 대입할 수 있습니다.
    • 채널에서 값을 받을 때까지만 대기합니다. 가져오면 바로 다음 코드를 실행합니다.

    위 그림을 보면 쉽게 이해할 수 있습니다. 아래 채널을 이용해 수정한 코드를 바로 실행해보세요.

    go
    실행 결과를 확인해보세요!
    default

    채널의 값을 수신할 때 꼭 변수에 대입하지 않아도 됩니다. 단지 <- 채널 형식으로 입력하면 수신을 받을 때까지 대기하고 별도의 값을 받지는 않습니다. 여기서 주의할 점은 위에서 고루틴B의 함수 종료 시점입니다. 고루틴B는 고루틴A로 송신한 데이터가 수신이 될때까지 대기합니다. 그런데 그 이후에 main() 함수(고루틴A)가 종료되어 프로그램이 종료되면 고루틴B는 끝까지 실행되지 않고, 종료되지 않은 채 프로그램이 종료될 수 있습니다.(채널의 역할이 끝났다면 고루틴의 본질은 비동기이기때문에) 따라서 데이터 송/수신 시점이 함수가 대기하는 시점과 관련있기 때문에 주의해야합니다.


    아래 채널의 값이 수신될때까지 대기하는 예시 코드를 바로 실행해보세요.

    go
    실행 결과를 확인해보세요!
    질문하기