Chapter1 자바 8,9,10,11 : 무슨 일이 일어나고 있는가?

허준기·2023년 8월 21일
0

자바

목록 보기
7/9

1.1 역사의 흐름은 무엇인가?

자바 역사를 통틀어 가장 큰 변화가 자바 8에서 일어났다. 예를 들어 다음은 사과 목록을 무게순으로 정렬하는 고전적 코드다.

Collections.sort(inventory, new Comparator<Apple>() {
	public int compare(Apple a1, Apple a2) {
    	return a1.getWeight().compareTo(a2.getWeight());
    }
});

자바8을 이용하면 자연어에 더 가깝게 간단한 방식으로 코드를 구현할 수 있다.

inventory.sort(comparing(Apple::getWeight));

멀티코어 CPU 대중화와 같은 하드웨어적인 변화도 자바 8에 영향을 미쳤다. 지금까지의 대부분의 자바 프로그램은 코어 중 하나만을 사용했다(즉, 나머지 코어는 유휴 idle 상태로 두거나, 운영체제나 바이러스 검사 프로그램과 프로세스 파워를 나눠서 사용)

자바8이 등장하기 이전에는 나머지 코어를 활용하려면 스레드를 사용하는 것이 좋았지만, 스레드를 사용하면 관리하기 어렵고 많은 문제가 발생할 수 있음 → 병렬 실행 환경을 쉽게 관리하고 에러가 덜 발생하는 방향으로 진화하려 노력

자바 8은 간결한 코드, 멀티코어 프로세서의 쉬운 활용이라는 두 가지 요구사항을 기반으로 함

  • 스트림 API
  • 메서드에 코드를 전달하는 기법
  • 인터페이스의 디폴트 메서드

1.2 왜 아직도 자바는 변화하는가?

새로운 언어가 등장하면서 진화하지 않은 기존 언어는 사장됨
우리는 시공을 초월하는 완벽한 언어를 원하지만 현실적으로 그런 언어는 존재하지 않으며 모든 언어가 장단점을 갖고 있음
자바는 지난 1995년 첫 베타 버전이 공개된 이후로 경쟁 언어를 대신하며 커다란 생태계를 성공적으로 구추구했다. 이제 자바가 어떻게 그러한 성공을 거뒀는지 살펴보자

1.2.1 프로그래밍 언어 생태계에서 자바의 위치

  • 자바는 처음부터 많은 유용한 라이브러리를 포함하는 잘 설계된 객체지향 언어로 시작
  • 코드를 JVM 바이트 코드로 컴파일하는 특징(그리고 모든 브라우저에서 가상 머신 코드를 지원하기) 때문에 자바는 인터넷 애플릿 프로그램의 주요 언어가 됨
  • JVM의 최신 업데이트 덥군에 경쟁 언어는 JVM에서 더 부드럽게 실행될 수 있으며, 자바와 상호동작할 수 있게 됨, 또한 다양한 임베디드 컴퓨팅 분야를 성공적으로 장악
     자바는 어떻게 대중적인 프로그래밍 언어로 성장했는가?
    → 객체지향은 1990년대에 두가지 이유로 각광받았다. 
      하나는 캡슐화 덕분에 C에 비해 소프트웨어 엔지니어링적인 문제가 훨씬 적다는 점이고, 
      다른 하나는 객체지향의 정신적인 모델 덕분에 윈도우 95 및 그 이후의 WIMP 프로그래밍 모델에 쉽게 대응할 수 있다는 점이다. 
      일단 만들면 모든 곳에서 실행할 수 있었다. 
    

자바8은 더 다양한 프로그래밍 도구 그리고 다양한 프로그래밍 문제를 더 빠르고 정확하며 쉽게 유지보수할 수 있다는 장점을 제공. 자바8에 추가된 기능은 자바에 없던 완전히 새로운 개념이지만 현재 시장에서 요구하는 기능을 효과적으로 제공

1.2.2 스트림 처리

스트림 : 한 번에 한 개씩 만들어지는 연속적인 데이터 항목들의 모임
자바8에서는 java.util.stream 패키지에 스트림 API가 추가됨. → 파이프라인을 만드는 데 필요한 많은 메서드 제공
스트림 API의 핵심은 기존에는 한 번에 한 항목을 처리했지만 자바8에서는 우리가 하려는 작업을(데이터베이스 질의처럼) 고수준으로 추상화해서 일련의 스트림으로 만들어 처리할 수 있다는 것이다
스레드라는 복잡한 작업을 사용하지 않으면서도 공짜로 병렬성을 얻을 수 있음

1.2.3 동작 파라미터화로 메서드에 코드 전달하기

코드 일부를 API로 전달하는 기능
자바8에서는 메서드(나의 코드)를 다른 메서드의 인수로 넘겨주는 기능 제공 → 내가 원하는 동작을 하도록 넘겨줌 → 동작 파라미터화
스트림 API는 연산이 동작을 파라미터화할 수 있는 코드를 전달한다는 사상에 기초

1.2.4 병렬성과 공유 가변 데이터

병렬성을 공짜로 얻을 수 있는 대신 스트림 메서드로 전달하는 코드의 동작 방식을 조금 바꿔야함
보통 다른 코드와 동시에 실행하더라도 안전하게 실행할 수 있는 코드를 만들려면 공유된 가변 데이터에 접근하지 않아야 한다.
공유된 변수나 객체가 있으면 병렬성에 문제가 발생하는데 이를 해결하기 위해서 synchronized를 이용해서 공유된 가변 데이터를 보호하는 규칙을 만들 수 있지만 이는 시스템 성능에 악영향을 미친다.
하지만 자바8 스트림을 이용하면 기존의 자바 스레드 API보다 쉽게 병렬성 활용

1.2.5 자바가 진화해야 하는 이유

자바8에서 함수형 프로그래밍을 도입함으로써 두 가지 프로그래밍 패러다임의 장점을 모두 활용 가능
언어는 하드웨어나 프로그래머 기대의 변화에 부응하는 방향으로 변화해야 한다. 자바는 계속 새로운 기능을 추가하면서 인기 언어의 자리를 유지하고 있다. 하지만 새로운 기능이 추가되었다고 하더라도 아무도 이용하지 않는다면 아무 소용이 없다.

이제 자바 8에 추가된 새로운 개념을 하나씩 자세히 살펴보자

1.3 자바 함수

프로그래밍 언어에서 함수라는 용어는 메서드 특히 정적 메서드와 같은 의미로 사용된다. 자바의 함수는 이에 더해 수학적인 함수처럼 사용되며 부작용을 일으키지 않는 함수를 의미

프로그래밍 언어의 핵심은 값을 바꾸는 것이다. 자바 프로그래밍 언어의 다양한 구조체가 값의 구조를 표현하는 데 도움이 될 수 있다. 하지만 프로그램을 실행하는 동안 이러한 모든 구조체를 자유롭게 전달할 수는 없다. 메서드, 클래스 등은 이급 자바 시민에 해당해 그 자체로는 값이 될 수 없다. 그런데 이 메서드를 일급 시민으로 만들면 프로그래밍에 유용하게 활용할 수 있다

1.3.1 메서드와 람다를 일급 시민으로

  • 메서드 참조 : 이 메서드를 값으로 사용해라
  • 프레디케이트(predicate) : 인수로 값을 받아 true나 false를 반환하는 함수 → boolean을 Boolean으로 변환하는 과정이 없으므로 더 효율적

1.3.3 메서드 전달에서 람다로

메서드를 값으로 전달하는 것은 유용한 기능이지만 한두 번만 사용할 메서드를 매번 저의하는 것을 귀찮음 → 익명함수/람다 이용
하지만 람다가 몇 줄 이상으로 길어진다면 코드가 수행하는 일을 잘 설명하는 이름을 가진 메서드를 정읠하고

1.4 스트림

거의 모든 자바 애플리케이션은 컬렉션을 만들고 활용
스트림 API를 이용하면 컬렉션 API와는 다른 방식으로 데이터 처리
컬렉션 : 반복 과정을 직접 처리 → 외부 반복
스트림 API : 라이브러리 내부에서 모든 데이터 처리 → 내부 반복

포킹 단계 : 두 CPU를 가진 환경에서 리스트를 필터링할 때 한 CPU는 리스트의 앞부분을 처리하고, 다른 CPU는 리스트의 뒷부분을 처리하도록 요청

1.6 함수형 프로그래밍에서 가져온 다른 유용한 아이디어

  • 메서드와 람다를 일급값으로 사용
  • 가변 공유 상태가 없는 병렬 실행을 이용해서 효율적이고 안전하게 함수나 메서드 호출Optional : 값을 갖거나 갖지 않을 수 있는 컨테이너 객체 → 값이 없는 상황을 어떻게 처리할지 명시적으로 구현하는 메서드 포함 → NullPointer 예외 피할 수 있음
profile
나는 허준기

0개의 댓글