3

I would like my Enum values to be comparable with other types, for instance, String. I am not entirely sure why it complains and what the error means.

enum class Fruits(val value: String): Comparable<String>{
    Apple("apple"),
    Orange("orange");

    override fun compareTo(other: String): Int {
        return compareValuesBy(this.value, other)
    }
}

val test: Boolean = Fruits.Apple == "apple"

Error says:

Type parameter T of 'Comparable' has inconsistent values: Fruits, String
David Soroko
  • 8,521
  • 2
  • 39
  • 51
Arturs Vancans
  • 4,531
  • 14
  • 47
  • 76
  • There are two issues, the major one is that `compareTo` is final in `Enum` so you may have to rethink your approach. The other one is that you need `Comparable` rather then `Comparable` – David Soroko Sep 19 '22 at 14:59
  • 2
    Also, implementing Comparable doesn't modify the implementation of `==`. That's managed by the `equals` function. But the contract for `equals` is that it must be reflexive. Since you cannot modify the `String.equals()` function, you cannot safely do this. – Tenfour04 Sep 19 '22 at 15:11
  • @Tenfour04 oh yeah, you are completely correct. I think I had a brain-fart. – Arturs Vancans Sep 19 '22 at 15:44

1 Answers1

4

Perhaps sealed classes are better suited to implement comparable enum, something like:

sealed class Fruit(val name: String) : Comparable<Fruit> {
    override fun compareTo(other: Fruit): Int = this.name.compareTo(other.name)
}

data object Apple    : Fruit("apple")
data object Orange   : Fruit("orange")
data object Zucchini : Fruit("zucchini")

fun main() {
    println(Apple < Orange)    // true
    println(Orange < Zucchini) // true
}
David Soroko
  • 8,521
  • 2
  • 39
  • 51