Praveen P.
Praveen P.

Reputation: 1106

Ignore elements when certain attribute is null when mapping objects

I am using the following function to map a network object to a domain one.

Mapping function

    fun getLocationLocalModel(input: LocationSearchResponse): List<Location> {
        return input.locations.map { location ->
            return@map location.bbox?.let {
                Location(
                    name = location.name,
                    countryCode = location.countryCode,
                    north = location.bbox.north,
                    south = location.bbox.south,
                    west = location.bbox.west,
                    east = location.bbox.east
                )
            }
        }.filterNotNull()
    }

Network DTOs

data class LocationSearchResponse(
    @SerializedName("geonames")
    val locations: List<Location>
)

data class Location(val bbox: Bbox?, val countryCode: String, val countryName: String,
                    val geonameId: Int, val lat: String, val lng: String, val name: String)

Domain Model

@Parcelize
data class Location(val name: String, val countryCode: String, val north: Double, val south: Double, val east: Double, val west: Double) : Parcelable

What I want is to ignore the objects where bbox is null so they are not added to the resulting list of locations. This function works, but there must be a better/simpler way to do this. Any help would be appreciated.

Upvotes: 0

Views: 264

Answers (1)

Kevin Coppock
Kevin Coppock

Reputation: 134664

As Animesh mentioned in the comments, simply change your statement to mapNotNull -- there's no need to use the return@ syntax there:

return input.locations.mapNotNull { loc ->
  loc.bbox?.let { bbox ->
    Location(loc.name, loc.countryCode, bbox.north, bbox.south, bbox.west, bbox.east)
  }
}

Alternatively you could filter first, then use !! to dereference:

return input.locations
  .filter { it.bbox != null }
  .map { loc->
    val bbox = loc.bbox!!
    Location(loc.name, loc.countryCode, bbox.north, bbox.south, bbox.west, bbox.east)
  }

Personally the former seems more readable to me.

Upvotes: 1

Related Questions