▸JAVA/라이브러리(API)

Comparator를 사용한 문자열 정렬 및 여러 개의 배열 객체 정렬

코데방 2020. 4. 19.
728x90

하나의 배열이 아닌 여러 개의 배열을 일정 기준으로 정렬하는 방법입니다. 혹시 sort() 메소드의 매개변수가 배열의 보이는 순서와 반대로 들어오는 것과, 음수가 리턴될 때 자리를 바꿔준다는 것을 모르시는 분은 아래 글을 먼저 읽고 오시는게 좋을 것 같습니다.

 

[JAVA/- 라이브러리(API)] - java.lang.Comparable / java.util.Comparator 사용법

 

 

사실 반대로 이해하고 있어도 정렬하는데 보통 지장이 없긴 하지만 해당 개념을 모르면 디버깅을 하거나 문제를 파악할 때 헷갈릴 수 있을 것 같습니다. 그리고 조금 더 응용을 하게 되면 매개변수의 위치와 리턴값의 설정이 중요해질 수 있습니다.

 


 

아래와 같은 두 배열이 있다고 가정하겠습니다. 두 배열을 내림차순으로 정렬하기 위해서는 각 배열을 같이 순회하면서 요소를 하나씩 비교하다가 먼저 작은 요소가 나오는 배열을 앞으로 가져와주면 됩니다. 아래 경우에는 test2가 앞으로 나와야 합니다. 

 

		int[] test1 = new int[] { 1, 2, 3, 5, 2, 10 };
		int[] test2 = new int[] { 1, 2, 3, 4, 2, 10 };

 

 

간단히 아래와 같이 Comparator를 설정해주면 됩니다. 역의 역으로 생각해서 o1, o2가 test1, test2의 순서라고 생각하고 양수가 리턴됐을 때 바꿔주고 음수나 0이 리턴됐을 때는 그대로 둔다라고 생각하면 됩니다. (다만 실제로는 반대로 o1, o2가 test2, test1 순서로 들어오고 -1이 리턴됐을 때 요소를 바꿔줍니다.)

 

배열의 정렬은 값이 다른 요소가 나오는 순간 결과를 리턴시켜야하기 때문에 모두 같은 값이면 for문 밖의 0이 리턴되고, 값이 크거나 작을 두 경우를 모두 for문안에서 리턴시켜줘야 하는 점에 주의하면 됩니다. 

 

package pojoPrj;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

public class Combination {
	public static void main(String[] ar) {

		int[] test1 = new int[] { 1, 2, 3, 5, 2, 10 };
		int[] test2 = new int[] { 1, 2, 3, 4, 2, 10 };

		List<int[]> arr = new ArrayList<>();
		arr.add(test1);
		arr.add(test2);

		arr.sort((o1, o2) -> {

			for (int i = 0; i < o2.length; i++) {

				if (o1[i] > o2[i]) {
					return 1;

				} else if (o1[i] < o2[i]) {
					return -1;
				}
			}

			return 0;
		});

		for (int[] t : arr) {
			System.out.println(Arrays.toString(t));
		}
	}
}

 

 


 

문자열의 정렬 또한 마찬가지입니다. 보통 String 클래스의 compareTo()를 써서 문자열을 비교합니다.

 

* string1.compareTo(string2)

 

package pojoPrj;

public class Combination {
	public static void main(String[] ar) {

		String test1 = "banana";
		String test2 = "apple";
		
		System.out.println(test1.compareTo(test2));

	}
}

 

이 메소드는 두 문자열의 값이 다를 때 "string1.charAt(i) - string2.charAt(i)" 결과를 리턴해줍니다. 즉 리턴값이 양수라면 string1이, 리턴값이 음수면 string2가 사전 순으로 뒷쪽에 있는 문자열입니다.

 

이 특성을 이용해 배열 간 정렬을 수행할 수 있습니다. 역시 이 경우에도 그냥 반대로 o1, o2가 test1, test2고 리턴값이 양수면 바꿔주고 0과 음수이면 그대로 둔다로 생각하면 될 것 같습니다. 

 

그리고 for문 안에서 클 경우와 작은 경우 모두 리턴값을 지정해줘야 합니다. 그렇지 않으면 요소의 값이 달라지는 순간 리턴시키지 못해 그냥 지나가므로 정렬이 제대로 수행되지 않습니다. 

 

package pojoPrj;

import java.util.Arrays;

public class Combination {
	public static void main(String[] ar) {

		String[] test1 = new String[] { "1", "2", "3", "5", "5", "6" };
		String[] test2 = new String[] { "1", "2", "3", "4", "5", "6" };
		String[][] arr = new String[][] {test1, test2};
		
		Arrays.sort(arr, (o1, o2) -> {
			
			for(int i = 0; i < o1.length; i++) {
				
				if(o1[i].compareTo(o2[i]) > 0) {
					return 1;
				} else if(o1[i].compareTo(o2[i]) < 0) {
					return -1;
				}
			}
			return 0;
		});
		
		for(String[] t : arr) {
			System.out.println(Arrays.toString(t));
		}
	}
}

 

728x90

댓글

💲 추천 글