Issue
I have a class with two enum fields representating type and charging status
enum class StationType {
TYPE_1,
TYPE_2,
FAST,
}
enum class ChargingEntityStatus {
AVAILABLE, // the best option
CHARGING,
RESERVED,
UNAVAILABLE, // the worst option
OCCUPIED
}
data class Station(
val stationId: Long,
val status: ChargingEntityStatus,
val type: StationType,
)
And I need to convert a list of these objects in that way: there can be two or more stations with the same type but different statuses values, but I need a list containing only one each type but with the best status value as the result and Available ones should come first.
For example, if I have a list of stations
listOf(
Station(1, StationType.TYPE_1, ChargingEntityStatus.CHARGING),
Station(9, StationType.TYPE_2, ChargingEntityStatus.UNAVAILABLE),
Station(3, StationType.TYPE_1, ChargingEntityStatus.AVAILABLE),
Station(7, StationType.FAST, ChargingEntityStatus.AVAILABLE)
)
that should convert to
listOf(
Station(3, StationType.TYPE_1, ChargingEntityStatus.AVAILABLE),
Station(7, StationType.FAST, ChargingEntityStatus.AVAILABLE),
Station(9, StationType.TYPE_2, ChargingEntityStatus.UNAVAILABLE),
)
because I need only one station of each type(like in a set), but also the AVAILABLE ones on the first places.
I've made this kind of algorithm, but I don't understand how to improve it:
if (stations.isNotEmpty()) {
val stationTypesMap = mutableMapOf<StationType, ChargingEntityStatus>()
stations.forEach {
if (stationTypesMap.contains(it.type)) {
val oldStatus = stationTypesMap[it.type] ?: ChargingEntityStatus.UNAVAILABLE
val newStatus = it.status
if (oldStatus.ordinal >= newStatus.ordinal) {
stationTypesMap[it.type] = newStatus
}
} else {
stationTypesMap[it.type] = it.status
}
}
val (available, unavailable) = stationTypesMap.entries
.partition { it.value == ChargingEntityStatus.AVAILABLE }
// then I'll be working with these two lists
}
Solution
enum class StationType {
TYPE_1,
TYPE_2,
FAST,
}
enum class ChargingEntityStatus {
UNAVAILABLE, // the worst option
RESERVED,
CHARGING,
AVAILABLE, // the best option
OCCUPIED
}
data class Station(
val stationId: Long,
val type: StationType,
val status: ChargingEntityStatus,
)
fun main(){
val temp = listOf(
Station(1, StationType.TYPE_1, ChargingEntityStatus.CHARGING),
Station(9, StationType.TYPE_2, ChargingEntityStatus.UNAVAILABLE),
Station(3, StationType.TYPE_1, ChargingEntityStatus.AVAILABLE),
Station(7, StationType.FAST, ChargingEntityStatus.AVAILABLE)
)
val filteredList = temp
.sortedByDescending { it.status }
.distinctBy { it.type }
.sortedByDescending { it.stationId }
.reversed()
.toList()
println(filteredList)
}
The main part is :
val filteredList = temp
.sortedByDescending { it.status }
.distinctBy { it.type }
.sortedByDescending { it.stationId }
.reversed()
.toList()
First of all, I sorted with the status. So the best status option will come first by .sortedByDescending { it.status }
. And I wanted to remove duplicated station type, so I used distinctBy
method. As it was sorted with the status, the low priority object will be removed. Lastly, I sorted with stationId and reversed it to make it ascending order by station id. And as you wanted as list, I added toList()
method.
I also wanted to reduce the time complexity, so I reversed the ChargingEntityStatus
enum class.
Answered By - Lee WonJoong
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.