Go 주니어 기술면접
새 면접Q. Go에서 slice와 array의 차이점은 무엇이며, 실무에서는 주로 어느 것을 사용하나요? 각각의 선언 방법과 함께 설명해주세요.
Array는 고정된 크기를 가지며 값 타입이고, slice는 가변 길이를 가지며 참조 타입입니다. Array는 [5]int와 같이 크기를 명시하여 선언하고, slice는 []int로 선언하거나 make([]int, 0, 10)으로 생성합니다. 실무에서는 크기가 동적으로 변할 수 있는 slice를 주로 사용하며, array는 크기가 명확히 정해진 경우나 성능이 중요한 특수한 상황에서만 사용합니다. Slice는 내부적으로 array를 가리키는 포인터, 길이, 용량 정보를 가지고 있어 유연한 데이터 처리가 가능합니다.
- • Array는 고정 크기 값 타입, slice는 가변 길이 참조 타입
- • 실무에서는 slice를 주로 사용
- • Slice는 포인터, 길이, 용량으로 구성
slice의 append 연산 시 용량이 부족하면 내부적으로 어떤 일이 일어나나요?
Q. 여러 goroutine에서 공유 변수에 동시에 접근하여 값을 증가시킬 때 발생할 수 있는 문제는 무엇이며, 이를 해결하기 위한 방법들을 설명해주세요.
Race condition이 발생하여 여러 goroutine이 동시에 읽고 쓰면서 예상과 다른 결과가 나올 수 있습니다. 해결 방법으로는 첫째, sync.Mutex를 사용하여 임계 영역을 보호하는 방법이 있습니다. 둘째, sync/atomic 패키지를 사용하여 원자적 연산을 수행할 수 있습니다. 셋째, channel을 통해 값을 전달하여 한 번에 하나의 goroutine만 접근하도록 할 수 있습니다. 간단한 카운터는 atomic을 사용하고, 복잡한 상태 관리는 mutex나 channel을 사용하는 것이 일반적입니다.
- • Race condition 문제 발생 가능
- • sync.Mutex로 임계 영역 보호
- • sync/atomic으로 원자적 연산
- • channel을 통한 동시성 제어
sync.Mutex와 sync.RWMutex의 차이점과 RWMutex를 사용하는 것이 유리한 상황은 언제인가요?
Q. Go의 net/http 패키지로 HTTP 서버를 만들 때, 미들웨어 패턴을 어떻게 구현할 수 있나요? 로깅 미들웨어를 예로 들어 설명해주세요.
미들웨어는 http.Handler를 받아서 새로운 http.Handler를 반환하는 함수로 구현합니다. 로깅 미들웨어는 func LoggingMiddleware(next http.Handler) http.Handler 형태로 정의하며, 내부에서 http.HandlerFunc를 반환합니다. 반환된 함수 안에서 요청 시작 시간을 기록하고, next.ServeHTTP를 호출하여 다음 핸들러를 실행한 후, 응답 시간과 상태 코드를 로그로 남깁니다. 여러 미들웨어는 체이닝 방식으로 연결하여 사용할 수 있으며, 인증, 로깅, CORS 등 공통 관심사를 분리할 수 있습니다.
- • http.Handler를 받아 http.Handler를 반환하는 함수 패턴
- • next.ServeHTTP 호출로 체이닝 구현
- • 공통 관심사 분리 가능
Gin이나 Echo 같은 웹 프레임워크를 사용하는 것과 표준 라이브러리만 사용하는 것의 장단점은 무엇인가요?
Q. Go에서 database/sql 패키지를 사용할 때 sql.DB의 연결 풀(connection pool)은 어떻게 관리되며, SetMaxOpenConns와 SetMaxIdleConns는 각각 어떤 역할을 하나요?
sql.DB는 내부적으로 연결 풀을 자동으로 관리하며, 필요할 때 연결을 생성하고 재사용합니다. SetMaxOpenConns는 데이터베이스에 동시에 열 수 있는 최대 연결 수를 제한하여 DB 서버의 과부하를 방지합니다. SetMaxIdleConns는 유휴 상태로 풀에 유지할 연결 수를 설정하여, 새로운 요청 시 연결 생성 비용을 줄입니다. 적절한 값 설정이 중요하며, 일반적으로 MaxIdleConns는 평균 동시 요청 수 정도로, MaxOpenConns는 DB 서버 용량을 고려하여 설정합니다.
- • sql.DB가 연결 풀 자동 관리
- • SetMaxOpenConns는 최대 연결 수 제한
- • SetMaxIdleConns는 유휴 연결 수 설정
- • 적절한 값 설정으로 성능 최적화
데이터베이스 트랜잭션을 처리할 때 defer를 사용한 롤백 처리 패턴에 대해 설명해주세요.
Q. Go에서 테스트 코드를 작성하는 방법과 testing 패키지의 기본 사용법을 설명해주세요. 테스트 파일명과 함수명 규칙도 함께 설명해주세요.
Go의 테스트는 testing 패키지를 사용하며, 테스트 파일은 _test.go 접미사를 가져야 합니다. 테스트 함수는 func TestXxx(t *testing.T) 형태로 작성하며, Test로 시작하고 대문자로 이어져야 합니다. t.Error나 t.Fatal을 사용하여 테스트 실패를 보고하고, go test 명령으로 실행합니다. 테이블 기반 테스트를 위해 구조체 슬라이스로 테스트 케이스를 정의하고 반복문으로 실행하는 패턴이 일반적입니다. 벤치마크는 func BenchmarkXxx(b *testing.B) 형태로 작성합니다.
- • _test.go 파일명 규칙
- • func TestXxx(t *testing.T) 함수 시그니처
- • go test 명령으로 실행
- • 테이블 기반 테스트 패턴 활용
테스트 커버리지를 확인하는 방법과 모킹(mocking)이 필요한 상황에서는 어떻게 처리하나요?
아직 댓글이 없습니다. 첫 번째 댓글을 남겨보세요!