문제 : 등록한 운송장 리스트의 배송 상태가 업데이트 될 때, 업데이트 된 배송 상태에 따라 리스트의 정렬이 필요했다.
다음과 같은 형태의 데이터를 가지는 TrackingInfoCompany 객체의 List를 정렬해야 한다.
data class TrackingInfoCompany {
val completeYN: String, // 배송완료 시 "Y", 아니면 "N"
val time: Long // 마지막 업데이트 시간 (millisecond 단위)
}
정렬 기준은 다음과 같다.
1. 배송 완료의 경우, 업데이트 시간에 관계 없이 가장 인덱스의 뒤에 위치.
(배송 완료 상태의 값끼리는 업데이트 시간 최근 순으로 인덱스 앞 위치)
2. 업데이트 시간이 최근 순으로 인덱스의 앞에 위치.
해결 :
이를 해결하기 위해서는 다음과 같은 함수가 필요했다.
1. 여러 개의 정렬 기준을 수행
2. 정렬 기준의 우선순위가 부여되어야 함. (A 기준을 통해 정렬 -> 그 상태에서 B 기준을 통해 정렬)
이러한 조건을 충족하기 위해 sortedWith()와 인자로 compareBy()를 사용하였다.
sortedWith()는 인자로 Comparator를 받아 여러 개의 정렬 기준을 둘 수 있으며, 원본 리스트를 바꾸지 않고 정렬된 리스트를 반환한다.
여러 개의 정렬 기준을 설정하는 Comparator는 compareBy()를 통해 정의 할 수 있다.
val sortedList = list.sortedWith(
compareBy(
{ 조건 A }, // 1. 조건 A에 대한 정렬 수행 후,
{ 조건 B } // 2. 1에서 정렬된 리스트를 기반으로 조건 B에 대한 정렬 수행
)
)
// list : 원본 리스트
// sortedList : 조건 A, B에 의해 정렬된 리스트
즉, 다음과 같이 원본 리스트 list에 대해 sortedWith()와 compareBy()를 사용하여 내부에 조건 block을 둘 수 있다.
이 때, compareBy()는 오름차순 정렬이다. 내림차순 정렬을 위해서는 compareByDescending()을 사용해야 한다.
위 sortedWith()와 compareBy()를 사용하여 문제를 해결한다.
val newList = list.sortedWith(
compareBy(
{ it.completeYN }, // 문자열 Y보다 N이 먼저이므로, 오름차순 정렬 시 Y는 N보다 뒤에 위치
{ -(it.time) }
// 오름차순 정렬이므로, 부호를 -로 변경하여 time의 값이 클수록 값이 작아져 앞에 위치
)
)
가장 먼저 completeYN의 값을 기준으로 오름차순 정렬을 수행한다.
문자열 정렬 시, N은 Y보다 앞에 위치하므로 오름차순 정렬 시 Y(배송완료) 는 자연스럽게 N보다 뒤에 위치하도록 정렬된다.
배송완료 여부에 따른 정렬을 수행한 후, 이를 기반으로 업데이트 시간에 따른 정렬을 수행한다.
time의 경우 millisecond 기준이므로 time의 값이 클수록 최근 시간임을 의미한다.
그러나 본 정렬의 경우 오름차순 정렬이므로 time의 값이 클수록 뒤에 위치한다.
그러므로 부호를 -로 변경하여 time의 값이 클수록(최근 시간일 수록) 인덱스의 앞에 위치할 수 있게 정렬한다.
'Android' 카테고리의 다른 글
[Android, Kotlin] Firebase DB에서의 각 Listener별 차이점 (Value, Single, Child) (2) | 2022.01.06 |
---|---|
[Android, Kotlin] ClipboardManager를 사용하여 기기에서 복사된 값 붙여넣기 (4) | 2021.12.13 |
[Android, Kotlin] RecyclerView에서 스크롤 시 Check box의 check 상태 보존 (0) | 2021.12.12 |
[Android, Kotlin] Bottom Navigation View + Jetpack Navigation 사용 시 fade animation 제거 (0) | 2021.12.09 |
[Android, Kotlin] Custom Dialog 만들기 (1) | 2021.12.07 |