함수형 프로그래밍은 함수를 사용하여 문제를 해결하는 것을 강조하는 프로그래밍 패러다임 중 하나 입니다.
함수형 프로그래밍의 주요 특징으로는 다음과 같습니다.
특징
- 불변성 : 함수형 프로그래밍에서 데이터는 불변입니다. 한번 생성되면 변경할 수 없습니다. 이렇게 함으로써 불변성을 가진 데이터를 사용하는 함수에 부작용(Side-Effect)가 없게 되어 프로그램이 동작하는 방식에 대해 좀 더 쉽게 추론할 수 있습니다.
- 또한 불변성의 또 다른 이점으로 동시성 프로그래밍 시에, 데이터의 불일치 문제를 해소할 수 있습니다. 불변성을 가진 데이터는 여러 스레드가 공유되는 한 데이터에 접근하더라도 변경이 불가능하기에, 동시성 상황에서 자주 일어날 수 있는 문제인 데이터 정합성 문제를 방지할 수 있습니다.
- 변경이 가능한 객체를 동시성 프로그래밍 상황에서 사용할 때, 잠금 이나 동기화 메커니즘을 통해 데이터 정합성 문제를 해결 할 수 있지만, 해당 메커니즘을 사용함으로써 성능이 저하될 수 있습니다. 하지만 불변성을 가진 객체를 사용한다면 멀티 쓰레드 환경에서도 데이터 정합성 문제가 발생하지 않게 코드를 작성할 수 있습니다.
public class Person {
private final String name;
private final int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public int getAge() {
return age;
}
}
- Java 에서는 field 값을 선언 할때 final 키워드로 선언하고, 또한 field 값에 대한 setter를 제공하지 않음으로써 불변 객체를 생성할 수 있습니다. 이렇게 생성된 객체는 읽기 전용 객체가 됩니다
- 고차 함수 : 함수형 프로그래밍에서 함수는 일급 시민입니다. 즉, 다른 함수에 인수로 전달될 수 있고, 값으로 반환될 수 있으며, 변수에 할당될 수 있습니다.
public class FirstCitizenExample {
public static void main(String[] args) {
// 문자열을 인자로 받아, 해당 문자열의 길이를 반환하는 함수를 변수로 선언
Function<String, Integer> getStringLength = s -> s.length();
String inputStr = "Hello,World";
// 메서드의 인자로 다른 함수를 넘길 수 있습니다.
int length = doSomethingWithString(inputStr, getStringLength);
System.out.println("입력 한 문자열 길이 : "+length);
}
private static int doSomethingWithString(String inputStr, Function<String, Integer> func) {
return func.apply(inputStr);
}
}
- 순수 함수 : 함수형 프로그래밍에서 함수는 순수합니다. 그 뜻은 부작용(Side-Effect)가 없으며 동일한 입력에 대해 항상 동일한 출력을 반환합니다.
public class PureFunctionExample {
public static int add(int a, int b) {
return a+b;
}
public static void main(String[] args) {
int result = add(10,20);
System.out.println(result);
int result2 = add(10,20);
System.out.println(result2);
}
}
반면에 사이드 이펙트가 존재하는 함수는 같은 입력에도 다른 출력을 반환하게 됩니다.
public class NonPureFunctionExample {
private static int sum = 0;
public static int add(int a, int b) {
sum += a+ b;
return sum;
}
public static void main(String[] args) {
int result1 = add(10, 20);
System.out.println(result1);
int result2 = add(10, 20);
System.out.println(result2);
}
}
함수 외부에 존재하는 sum 이라는 변수를 갖게 되고, 그에 따라 함수 외부에 저장된 sum값이 add 메서드가 진행됨에 따라 값이 누적되면서, 동일한 입력값에도 다른 출력을 보여주게 됩니다.
함수형 프로그래밍의 주요특징에 대해 간략히 알아봤습니다. 이러한 함수형 프로그래밍의 장단점은 무엇이 있을까요?
장점
- 프로그램 동작에 대해 쉽게 추론
- 함수형 프로그래밍을 사용하면 코드를 더 간결하고 읽기 쉽게 유지하기 좋습니다.
- 자바에서는 Java 8 이후 추가된, lambda와 stream을 이용할 수 있습니다.
- 멀티 쓰레드 환경에서도 Thread-safety를 유지할 수 있습니다.
- 여러 개의 쓰레드가 동시에 한 데이터에 접근하게 되더라도, 해당 데이터는 불변성을 가진 수정이 불가능한 데이터이기에, 쓰레드에 안전하게 코드를 작성할 수 있습니다.
- 또한 순수 함수를 사용하기 때문에, 함수 자체의 사이드 이펙트가 없기에 병렬처리를 사용할 수 있고, 병렬 처리에 적합하다 할 수 있습니다.
- 불변성과 순수 함수를 사용함으로써, 작성한 프로그램의 동작에 대해 추론을 쉽게 해 버그를 줄일 수 있습니다.
단점
- 러닝 커브가 높습니다
- 함수형 프로그래밍에서 병렬 연산이나, Lazy-Evaluation(지연 평가) 또는 커링과 같은 일부 요소는 프로그램의 추가 오버헤드를 유발할 수도 있습니다.
참고 자료
'프로그래밍 > Java' 카테고리의 다른 글
소수 계산 어떻게 해결해야할까? (0) | 2023.09.16 |
---|---|
Java volatile이란? (0) | 2023.09.08 |
G1 GC에 대해 (0) | 2023.03.31 |
Singleton 패턴과 스프링에서는 Singleton 패턴을 어떻게 사용하고 있을까? (0) | 2023.01.27 |
Long 과 AtomicLong은 어떤 차이가 있을까? (0) | 2023.01.24 |