Returns the second line if empty at first?
Here is the idiom I find myself.
def chooseName(nameFinder: NameFinder) = {
if(nameFinder.getReliableName.isEmpty) nameFinder.getReliableName
else nameFinder.secondBestChoice
}
To avoid having to be called getReliableName()
twice on nameFinder
, I add code that makes my method less elegant.
def chooseName(nameFinder: NameFinder) = {
val reliableName = nameFinder.getReliableName()
val secondBestChoice = nameFinder.getSecondBestChoice()
if(reliableName.isEmpty) reliableName
else secondBestChoice
}
This seems messy because I am creating unnecessary amount of state with help vals
for no reason other than to prevent the method from being called again. Scala taught me that whenever I feel dirty, there is almost always a better way.
Is there a more elegant way to write this?
Here two Strings, return whichever isn't empty while favoring the first
source to share
There is no need to always call getSecondBestChoice
, of course. Personally, I don't find anything illogical in the code after changing it - it is clear what it does, it has no mutable state. The other answers just seem tricky to avoid usingval
def chooseName(nameFinder: NameFinder) = {
val reliableName = nameFinder.getReliableName()
if(reliableName.isEmpty) reliableName
else nameFinder.getSecondBestChoice()
}
If you really want to avoid val, here's another option (generalizes well if there are more than two alternatives)
List(nameFinder.getReliableName(), nameFinder.getSecondBestChoice()).find(_.nonEmpty).get
(or getOrElse(lastResort)
, if everything in the list can be empty as well)
source to share
Option(namefinder.getReliableName) // transforms a potential null into None
.filter(_.trim.nonEmpty) // "" is None, but also " "
.getOrElse(nameFinder.secondBestChoice)
Or better, if you can change getReliableName
to return Option[String]
:
def chooseName(nameFinder: NameFinder): String =
namefinder.getReliableName getOrElse nameFinder.secondBestChoice
Finally, if secondBestChoice
it can fail as well (assuming it returns Option[String]
):
def chooseName(nameFinder: NameFinder): Option[String] =
namefinder.getReliableName orElse nameFinder.secondBestChoice
source to share
If you need it more than once:
scala> implicit class `nonempty or else`(val s: String) extends AnyVal {
| def nonEmptyOrElse(other: => String) = if (s.isEmpty) other else s }
defined class nonempty
scala> "abc" nonEmptyOrElse "def"
res2: String = abc
scala> "" nonEmptyOrElse "def"
res3: String = def
source to share