Add bin search

This commit is contained in:
Joren 2024-04-30 02:02:39 +02:00
parent fd122ec376
commit 84e801ed01
Signed by untrusted user who does not match committer: Joren
GPG Key ID: 280E33DFBC0F1B55

View File

@ -39,10 +39,11 @@ class PokeSearchViewModel(private val favouritesRepository: FavouritesRepository
fun search(query: String) { fun search(query: String) {
viewModelScope.launch { viewModelScope.launch {
try { try {
val filteredList = _initialPokemonList.value?.filter { it.name.startsWith(query, ignoreCase = true) } val filteredList = _initialPokemonList.value?.binarySearch(query)
val detailsList = mutableListOf<PokemonDetails>() val detailsList = mutableListOf<PokemonDetails>()
if (filteredList != null) { if (filteredList != null) {
for (pokemonSpecies in filteredList.take(SHOW_LIMIT)) { for (index in filteredList until minOf(_initialPokemonList.value?.size ?: 0, filteredList + SHOW_LIMIT)) {
val pokemonSpecies = _initialPokemonList.value!![index]
val details = service.getPokemonDetails(extractPokemonId(pokemonSpecies.url)) val details = service.getPokemonDetails(extractPokemonId(pokemonSpecies.url))
val isFavorite = favouritesRepository.isFavourite(details.id) val isFavorite = favouritesRepository.isFavourite(details.id)
detailsList.add(details.copy(isFavorite = isFavorite)) detailsList.add(details.copy(isFavorite = isFavorite))
@ -55,6 +56,21 @@ class PokeSearchViewModel(private val favouritesRepository: FavouritesRepository
} }
} }
private fun List<PokemonSpecies>.binarySearch(query: String): Int {
var low = 0
var high = this.size - 1
while (low <= high) {
val mid = (low + high) ushr 1
val comparison = this[mid].name.compareTo(query, ignoreCase = true)
when {
comparison == 0 -> return mid
comparison < 0 -> low = mid + 1
else -> high = mid - 1
}
}
return low
}
private fun extractPokemonId(url: String): Int { private fun extractPokemonId(url: String): Int {
val parts = url.split("/") val parts = url.split("/")
return parts[parts.size - 2].toInt() return parts[parts.size - 2].toInt()