탄탄대로
[Level 1] 제일 작은 수 제거하기 본문
- 방법이 많구나, 많아!
문제
"정수를 저장한 배열, arr 에서 가장 작은 수를 제거한 배열을 리턴하는 함수, solution을 완성해주세요. 단, 리턴하려는 배열이 빈 배열인 경우엔 배열에 -1을 채워 리턴하세요. 예를들어 arr이 [4,3,2,1]인 경우는 [4,3,2]를 리턴 하고, [10]면 [-1]을 리턴 합니다."
입출력 예
arr | return |
[4,3,2,1] | [4,3,2] |
[10] | [-1] |
풀이
class Solution {
public int[] solution(int[] arr) {
int[] answer = null;
int min = arr[0]; //최소값 저장 변수
if(arr.length == 1){ //비교할 대상이 없을 경우 -1 반환
answer = new int[]{-1};
return answer;
}
//최소값 구하기
for(int x = 0; x < arr.length; x++){
if(min < arr[x]){
min = arr[x];
}
}
//최소값을 제외한 배열 만들기
for(int i = 0; i < arr.length; i++){
if(arr[i] == min){ //배열에서 최소값의 위치에 도달
answer = new int[arr.length-1]; //배열 생성
for(int y = 0; y < i; y++){ //최소값 전까지 배열 값 저장
answer[y] = arr[y];
}
for(int z = i; z < arr.length-1; z++){ //최소값 이후의 값 저장
answer[z] = arr[z+1];
}
break;
}
}
return answer;
}
}
다른 클래스를 사용하지 않고 배열 그대로를 가지고 풀어보고 싶었다.
배열은 크기가 고정이기 때문에 ArrayList처럼 요소를 넣었다, 뺐다를 할 수 없다.
그래서 최소값의 인덱스를 구해서 for문으로 최소값까지 도달했을때 그 인덱스 값만 빼고 새로운 배열에 넣어야지, 까지는 생각했는데 배열의 크기가 다르다보니 인덱스가 달라서 값을 넣는 부분에서 막히고 말았다.
그래서 검색..!
검색했더니 저런 방법이 있었다! 나는 왜 저기까지 생각을 못했을까!
이외에도 자바에서 배열의 요소를 제외하는 방법은 많다.
다른 사람 풀이와 검색 결과를 봤을때 대다수 사용하는 방법을 정리해보았다.
1. ArrayList 사용
import java.util.ArrayList;
import java.util.List;
import java.util.Arrays;
import java.util.Collections;
class Solution {
public int[] solution(int[] arr){
int[] answer = {};
if(arr.length == 1){ //비교할 값이 없을 경우 -1 반환
return answer = new int[]{-1};
}
List<Integer> arrayList = new ArrayList<Integer>(); //리스트 생성
for(a : arr){
arrayList.add(a); //배열의 요소를 리스트에 넣기
}
Integer min = Collections.min(arrayList); //리스트의 최소값 추출
arrayList.remove(min); //리스트에서 값 삭제
answer = new int[arr.length-1];
for(int i = 0; i < arrayList.size(); i++){ //배열에 리스트 요소 넣기
answer[i] = arrayList.get(i);
}
return answer;
}
}
Collections.min()
Collections Class
- Collection에서 작동하거나 반환하는 정적 메소드로만 구성된다.
- Collection에서 작동하는 다형성 알고리즘이 포함되어 있다.
☞ Collection 인터페이스를 구현한 클래스에 대한 객체생성, 정렬, 병합, 검색 등의 기능(알고리즘)을 안정적으로 수행하도록 도와주는 유틸리티 클래스이다.
- Collections는 클래스이며, 이 클래스 안에 있는 메소드는 static이기 때문에 인스턴스 생성 없이 바로 사용할 수 있다.
리턴 | 설명 |
static <T extends Object & Comparable<? super T>> T | min(Collection<? extends T> coll)
요소의 자연스러운 순서에 따라 지정된 컬렉션의 최소 요소를 반환합니다 .
|
arrayList.remove()
ArrayList의 값을 삭제하는 메소드
리턴 | 설명 |
E | remove(int index)
이 목록의 지정된 위치에 있는 요소를 제거합니다.
|
파라미터로 전달된 인덱스 위치의 값을 리스트에서 삭제하고 그 객체를 반환.
리턴 | 설명 |
boolean | remove(Object o)
전달한 요소가 있는 목록에 있는 경우 지정된 요소의 첫 번째 항목을 제거합니다.
|
파라미터로 삭제하려는 값을 전달하고 리스트에 그 값이 있을 경우 삭제하고 true를 반환.
※ remove() 메소드는 파라미터 값에 따라 실행하는 것이 달라짐
2. Arrays.sort 사용
import java.util.*;
import java.util.stream.Collectors;
class Solution {
public int[] solution(int[] arr) {
List<Integer> list = Arrays.stream(arr).boxed().collect(Collectors.toList());
Arrays.sort(arr);
list.remove(list.indexOf(arr[0]));
if(list.size() <= 0){
return new int[]{-1};
}
return list.stream().mapToInt(i->i).toArray();
}
}
Stream.boxed()
boxed() 메소드는 IntStream 같이 원시 타입에 대한 스트림 지원을 클래스 타입(예: IntStream -> Stream<Integer>)으로 전환하여 전용으로 실행 가능한 (예를 들어 본문과 같이 int 자체로는 Collection에 못 담기 때문에 Integer 클래스로 변환하여 List<Integer> 로 담기 위해 등) 기능을 수행하기 위해 존재합니다.
3. System.arraycopy 사용
class Solution {
private int[] removeElement(int[] original, int element){
int[] n = new int[original.length -1];
System.arraycopy(original, 0, n, 0, element);
System.arraycopy(original, element+1, n, element, original.length-element-1);
return n;
}
public int[] solution(int[] arr) {
int min = arr[0];
int minIdx = 0;
if(arr.length == 1){
return new int[]{-1};
}
for(int i = 0; i < arr.length; i++){
if(min > arr[i]){
min = arr[i];
minIdx = i;
}
}
return removeElement(arr, minIdx);
}
}
System.arraycopy();
소스 배열을 지정된 시작 위치에서 대상 배열로 복사합니다. 복사할 인수의 수는 인수에 의해 결정됩니다.
System.arraycopy(src, srcPos, dest, destPos, length);
src - 원본 배열
srcPos - 원본 배열의 복사 시작 위치
dest - 복사할 배열
destPost - 복사할 배열의 복사 시작 위치
length - 복사할 요소의 개수
//출처: https://tosuccess.tistory.com/169
import java.util.Arrays;
class CodeRunner{
public static void main(String[] args){
int[] arr = {12, 45, 10, 55, 31};
int[] resultArr = solution(arr);
System.out.println("result : "+Arrays.toString(resultArr)); //result : [12, 45, 55, 31]
}
private static int[] removeElement(int[] original, int index){
int[] n = new int[original.length -1];
System.arraycopy(original, 0, n, 0, index);
System.out.println("[removeElement] original first copy : "+ Arrays.toString(n));
//[removeElement] original first copy : [12, 45, 0, 0]
System.arraycopy(original, index+1, n, index, original.length-index-1);
System.out.println("[removeElement] original second copy : "+ Arrays.toString(n));
//[removeElement] original second copy : [12, 45, 55, 31]
return n;
}
public static int[] solution(int[] arr) {
int min = arr[0];
int minIdx = 0;
if(arr.length == 1){
return new int[]{-1};
}
for(int i = 0; i < arr.length; i++){
if(min > arr[i]){
min = arr[i];
minIdx = i;
}
}
System.out.println("[solution] minIdx : "+minIdx); //[solution] minIdx : 2
return removeElement(arr, minIdx);
}
}
4. Stream 사용
import java.util.Arrays;
import java.util.stream.IntStream;
class Solution {
public int[] solution(int[] arr){
int[] answer = {};
int min = arr[0];
int minIdx = 0;
if(arr.length == 1){
return answer = new int[]{-1};
}
for(int i = 0; i < arr.length; i++){
if(min > arr[i]){
min = arr[i];
minIdx = i;
}
}
return remove(arr, minIdx);
}
private int[] remove(int[] a, int index){
return IntStream.range(0, a.length)
.filter(i -> i != index)
.map(i -> a[i])
.toArray();
}
}
코드 분석
IntStream.range(int startInclusive, int endInclusive)
리턴 | 설명 |
IntStream | startInclusive(포함)에서부터 endInclusive(미포함)까지 1씩 점증적으로 증가한 InputStream을 처음부터 순서대로 정렬하여 반환합니다. |
IntStream.filter()
리턴 | 설명 |
IntStream | 주어진 조건과 일치하는 요소로 구성된 스트림을 반환합니다. |
IntStream.map()
리턴 | 설명 |
IntStream | 주어진 함수를 이 스트림의 요소에 적용한 결과로 구성된 스트림을 반환합니다. |
IntStream.toArray()
리턴 | 설명 |
int[ ] | 이 스트림의 요소를 포함하는 배열을 반환합니다. |
참고
- https://www.delftstack.com/ko/howto/java/java-remove-element-from-array-and-shift/
- https://www.techiedelight.com/ko/remove-element-specific-index-array-java/
문제 출처: 프로그래머스
'코딩테스트' 카테고리의 다른 글
[Level 1] 정수 내림차순으로 배치하기 (0) | 2022.08.01 |
---|---|
[Level 1] 이상한 문자 만들기 (0) | 2022.07.27 |
[Level 1] 콜라츠 추측 (0) | 2022.07.19 |
[Level 1] 평균 구하기 (0) | 2022.07.18 |
[Level 1] 하샤드 수 (0) | 2022.07.13 |