-
[프로그래머스 1단계] 알고리즘 2. 최대값과 최소값24년 11월 이전/레거시-알고리즘(3) 2018. 2. 12. 23:41반응형
문제 출처는 프로그래머스 알고리즘 연습 에서 볼 수 있습니다!(https://programmers.co.kr/learn/challenges)
알고리즘 2. 최대값과 최소값 구하기. 입력값은 "숫자(공백)숫자(공백)... 숫자" 이런 형식의 문자열이다. 이 문자열에서 최대값과 최소값을 찾아 "최소값(공백)최대값" 형식의 문자열을 반환하는 함수를 만드시오.
public class GetMinMaxString {
public String getMinMaxString(String str) {
return "";
}
public static void main(String[] args) {
String str = "1 2 3 4";
GetMinMaxString minMax = new GetMinMaxString();
//아래는 테스트로 출력해 보기 위한 코드입니다.
System.out.println("최대값과 최소값은?" + minMax.getMinMaxString(str));
}
}
풀이 : 이번에는 자바8 스트림 API를 이용하여 함수형 프로그래밍으로 문제를 풀어볼 것이다. 먼저 어떻게 풀어야할지 생각해보자. 나의 방식은 이러했다.
1. 주어진 입력 문자열을 통해서 숫자로 된 문자열들을 추출한다.
2. 숫자로 된 문자열들을 숫자로 바꾼다.
3. 바뀐 숫자들을 정렬하여 최대값 최소값을 구한다.
그렇다면 이제 실제로 입력값인 문자열 str에서 숫자를 추출해보자. 이 작업은 자바의 String 클래스의 split 메소드를 이용하면 쉽게 풀 수 있다. 문자열 형식을 다시 한 번 보자.
"숫자(공백)숫자(공백)....숫자" -> "-1 5 3 2 0 1 4"
이런식으로 문자열의 형식이 정해져있다. 여기서 잠깐 split 메소드를 살펴보자. API에 따르면
String[] split(String regex);
로 되어 있다. 그렇다. split 메소드는 정규표현식에 따라 문자열을 쪼개서 문자열 배열을 만들어주는 함수이다. 우리가 제거해야할 문자들은 공백 문자이다. 따라서
str.split(" "); -> ["-1", "5", "3", "2", "0", "1", "4"]
를 호출하면 숫자로 이루어진 문자열 배열을 얻을 수 있다. 자 첫번째 단계가 끝났다. 이제 문자열들을 숫자로 바꿔야한다. 이는 Stream API의 map 메소드로 쉽게 풀이가 가능하다. 물론 그 전에 split을 통해 얻은 문자열 배열을 컬렉션으로 바꿔야 한다. 왜냐하면 기본적으로 스트림API는 컬렉션에만 제공이 되기 때문이다.(물론 자바는 기본형에 대한 스트림도 지원합니다. 예를 들어 IntStream 같은 것들이 그 지원 중 하나죠)
문자열 배열을 컬렉션으로 바꾸기 위해서 Arrays.asList() 함수를 이용할 것이다.
list = Arrays.asList(str.split(" ")); -> String[] => List<String>
스트림 사용법은 그 컬렉션에 stream()를 이용하면 된다. 자 이제 스트림을 사용할 준비가 다 되었다. 이제 두 번째 단계 추출한 숫자인 문자열들을 정수형 숫자로 바꿔보자.
list = list.stream() List<String> -> Stream<String>
.map( s -> Integer.parseInt(s)) Stream<String> -> Stream<Integer>
.collect(Collectors.toList()); Stream<Integer> -> List<Integer>이는 컬렉션 요소의 타입을 String에서 Integer 타입으로 변환시킨다. 여기서
s -> Integer.parseInt(s)
부분은 람다식인데 간단히 입력값 String s를 Integer.parseInt(s)를 통하여 정수값을 출력시키는 부분이다. map은 이렇게 개발자가 각 요소를 원하는 타입으로 모조리 바꿔버릴때 유용하다. 이제 마지막 단계인 정렬을 해보자. Collectors.sort 메소드를 이용할 것이다.
Collectors.sort(list, (i1, i2) -> i1.compareTo(i2));
sort는 첫번째로 컬렉션을 두번째로 그 비교해서 정렬시킬 수 있는 람다를 넣어주면 된다. 이러면 내림차순으로 정렬된다. 그러니 이제 "최소값(공백)최대값" 형식의 결과를 출력시키면 된다.
int min = list.get(0);
int max = list.get(list.size()-1);
return min + " " + max;
다음은 나의 코드 본문이다.
import java.util.*;
import java.util.stream.Collectors;
public class GetMinMaxString {
public String getMinMaxString(String str) {
List<Integer> list = Arrays.asList(str.split(" "))
.stream()
.map(s -> Integer.parseInt(s))
.collect(Collectors.toList());
Collections.sort(list, Integer::compare);
int min = list.get(0);
int max = list.get(list.size()-1);
/* stream api를 이용하여 끝까지 구한 코드
int max = list.stream()
.max(Integer::compare)
.get();
int min = list.stream()
.min(Integer::compare)
.get();
*/
return min + " " + max;
}
public static void main(String[] args) {
String str = "1 2 3 4";
GetMinMaxString minMax = new GetMinMaxString();
//아래는 테스트로 출력해 보기 위한 코드입니다.
System.out.println("최대값과 최소값은?" + minMax.getMinMaxString(str));
}
}
후 stream api를 이용하여 표현하는게 쉽지가 않구나...
728x90'레거시 > 레거시-알고리즘(3)' 카테고리의 다른 글
[프로그래머스 1단계] 알고리즘 6. 같은 숫자는 싫어! (0) 2018.02.21 [프로그래머스 1단계] 알고리즘 5. 행렬 합 (0) 2018.02.20 [프로그래머스 1단계] 알고리즘 4. 가장 작은 수 제거하기 (0) 2018.02.13 [프로그래머스 1단계] 알고리즘 3. 피보나츠 수열 (0) 2018.02.12 [프로그래머스 1단계] 알고리즘 1. 최대공약수 최소공배수 구하기 (0) 2018.02.05