문제 출처 : https://school.programmers.co.kr/learn/courses/30/lessons/120817
문제
--
--
풀이
--
class Solution {
public double solution(int[] numbers) {
double sum = 0;
for(int i = 0; i < numbers.length; i++){
sum += numbers[i];
}
return sum / numbers.length;
}
}
--
다른 풀이
--
import java.util.Arrays;
class Solution {
public double solution(int[] numbers) {
return Arrays.stream(numbers).average().orElse(0);
}
}
--
비교 및 회고
--
배열을 스트림으로 변환하여 사용하는 방법을 생각하지 못했다.
두 방법의 장단점과 무엇이 더 효율적인지 궁금해졌다.
성능적인 측면 (속도)
for문
- 직접 반복 제어를 하므로 필요한 경우 반복 중간에 접근(제어) 가능
- 자바 컴파일러는 상대적으로 for문이 더 최적화하기 쉬운 구조 (빠르게 실행 가능)
- 별도의 오버헤드 없이 접근 가능
Stream API
- 함수형 스타일로 동작하여, 따로 세부 사항에 대해 신경 쓸 필요가 없다.
(다만 이러한 이유로 (추상화) 미세한 성능 오버헤드 발생 가능성 있음) - 쉽게 병렬처리를 할 수 있어 다중 코어 환경에서 성능을 크게 향상 가능 (큰 배열 처리)
- 래퍼 클래스(Integer, Long)을 사용하기 때문에 기본형 타입을 다룰 때는 박싱/언박싱으로 인한 성능 저하가 발생할 수 있음 (그래서 IntStream, LongString 등을 사용해야 함)
효율성인 측면
for문
- 간단하게 메모리를 사용하므로 메모리 효율성이 상대적으로 좋음
- 인덱스를 명시적으로 관리할 수 있으므로 인덱스가 중요한 경우 더 효율적인 접근 방식을 사용할 수 있다.
Stream API
- 내부적으로 최적화된 연산을 제공하여, 큰 데이터셋을 처리할 때 좋다.
코드 가독성 & 유지보수성
for문
- 코드가 직관적이므로 이해하기 편하다.
- 다만 과정이 많아지면 코드 수가 길어지고 보기 힘들어질 수도 있다.
Stream API
- 상대적으로 코드 수를 줄여 간결하게 작성할 수 있다.
- 내부적으로 함수를 사용하기 때문에 함수들의 내용을 알고 있다면 가독성이 좋아 질 수 있다.
- 다만 람다식이나 메서드 참조를 많이 사용하게 되면 디버깅이 어려워질 수 있으며, 복잡한 연산에서 유지보수가 어려워 질 수도 있다.
병렬 처리
for문
- 수동으로 스레드나 스레드 풀을 관리해야 하므로 구현이 복잡하고 오류가 발생할 가능성이 높다.
- 다만 이를 이용하여 실행 순서를 세밀하게 제어할 수는 있지만 이 또한 복잡한 코드로 이어진다.
Stream API
- 쉽게 병렬 처리를 구현하는 함수를 제공하고 있어 큰 데이터셋에서 성능을 극대화할 수 있다.
- 다만 추가적으로 스레드 안전성을 보장하며 관리가 필요하지만 for문 보다는 간편하다.
성능적인 측면에서는 for문이 더 좋아 보인다.
직접 제어도 가능하며 자바 컴파일러에서는 for문이 더 최적화하기 쉬운 구조다.
그래서 상대적으로 속도도 빠르며, 별도의 오버헤드도 없다.
그래서 속도적인 측면만 바라본다면 for문이 더 좋아보이지만
여러 상황들을 고려해보면 Stream API를 사용하는 것이 더 좋아보인다.
물론 상황에 따라 유동적으로 알맞는 방법을 찾아서 해야겠지만
지금 생각하기에는 for문을 사용하는 것보다 Stream에 더 익숙해지면
활용도가 더 높아질 것이라 생각하기 때문에 Stream을 자주 사용하는 방식으로 노력해야겠다고 생각한다.
--
'Record > 알고리즘 풀이' 카테고리의 다른 글
[ Lv.0 / 산술 ] 나이 출력 (+ 변수 생략 후 바로 계산 및 출력 ) (0) | 2024.08.23 |
---|---|
[ Lv.0 / 비교 ] 숫자 비교하기 (+ if문, 삼항 연산자 ) (0) | 2024.08.23 |