프로그래밍백엔드 개발자

Kotlin에서 가시성 수정자(visibility modifiers)란 무엇이며, 그것이 캡슐화 및 애플리케이션 아키텍처에 미치는 영향은 무엇인가요?

Hintsage AI 어시스턴트로 면접 통과

답변.

문제 배경:

가시성 수정자(visibility modifiers)는 Kotlin의 핵심 기능으로, Java에서 상속 및 개선되었습니다. 이를 통해 클래스, 함수 및 속성에 대한 접근을 제한하여 최선의 캡슐화 및 모듈화 관행을 지원합니다.

문제:

가시성을 잘못 사용하면 아키텍처의 계층이 무너지거나 구현이 외부로 유출되거나 반대로, 필요한 곳에서 클래스 및 메소드에 접근이 불가능해질 수 있습니다. 이러한 오류는 종종 너무 늦게 발견됩니다.

해결책:

Kotlin에는 네 가지 가시성 수정자가 있습니다:

  • public — 어디에서나 접근 가능 (기본값)
  • internal — 하나의 모듈 내에서만 접근 가능
  • protected — 클래스와 그 하위 클래스 내에서만 접근 가능
  • private — 파일, 클래스 또는 객체 내에서만 접근 가능

코드 예:

open class Base { private fun onlyBase() {} protected fun baseAndDerived() {} internal fun insideModule() {} public fun anyone() {} } class Derived : Base() { fun test() { baseAndDerived() // 접근 가능 // onlyBase() — 오류 } }

주요 특징:

  • internal은 Kotlin에 특화되어 있으며, Java에서는 사용되지 않음
  • top-level 요소에 대한 수정자는 특별히 작동: private는 파일로 가시성을 제한
  • 인터페이스의 모든 메소드와 속성은 기본적으로 public

함정 질문.

라이브러리를 게시할 때 internal 수정자는 어떻게 작동하나요?

internal은 하나의 모듈 내에서 요소를 숨기지만, 라이브러리를 jar/aar로 컴파일하면 internal 요소는 리플렉션을 통해 볼 수 있습니다.

클래스 속성에 대한 private와 top-level 함수에 대한 private는 어떻게 다르나요?

클래스 속성에 대한 private는 클래스에 의해서만 가시성을 제한하지만, top-level에서는 선언된 파일에 대해서만 가시성을 제한합니다.

top-level 함수에 protected를 적용할 수 있나요?

아니요, protected는 클래스 또는 인터페이스의 멤버에 대해서만 가능합니다. top-level에는 protected를 사용할 수 없어 컴파일 오류가 발생합니다.

전형적인 오류 및 안티 패턴

  • 불필요하게 열려 있는 클래스와 함수 (public 없이 필요 없음)
  • 독립적인 구성 요소를 통합하는 모듈에서 internal 사용
  • top-level 함수나 속성에 protected 사용 시도

실제 사례

부정적인 사례

대규모 라이브러리가 거의 모든 API를 public으로 선언하여 유틸리티 및 헬퍼를 포함시켰습니다. 그 결과 사용자는 구현 세부 사항에 의존하게 되었습니다.

장점:

  • 모든 사용자의 사용 용이성

단점:

  • 하위 호환성 및 리팩토링의 어려움

긍정적인 사례

필요한 클래스만 public으로 선언하고 나머지는 internal 또는 private로 설정하여 가시성 수준을 명확하게 분리하였습니다.

장점:

  • 제어된 접근, 용이한 내부 변경

단점:

  • 아키텍처 가이드 지원과 설계 시 주의가 필요함