Hi guys. Any idea to improve this? ```val animals:...
# announcements
z
Hi guys. Any idea to improve this?
Copy code
val animals: List<Animal> = ....
val animalToChangeColor = animals[0]

val newColor = ....
val newAnimal = when {
    animalToChangeColor is Cat -> {
        animalToChangeColor.copy(color = newColor)
    }

    animalToChangeColor is Sheep -> {
        animalToChangeColor.copy(color = newColor)
    }

    animalToChangeColor is Dog -> {
        animalToChangeColor.copy(color = rnewColor)
    }
}
Imagine
Cat
,
Sheep
and
Dog
are data classes that implement
Animal
interface which has
color
field. It seems impossible to "polyphormise" this, but maybe i'm missing some awesome Kotlin feature 😛
c
I believe you can do is Animal, but you would need an else block. Another option is to list them separated by commas.
Copy code
animal is Dog, animal Is Cat, animal is Sheep -> {}
Or if all of the sealed class implementations have a colour, then just add it to the sealed class as a property.
z
that doesn't work because copy method doesn't exist in any Type declaration that all three animal types inherit from. Each of them have the copy method but its not the same method.
c
Ah I see now what the actual problem is. I’m surprised I’ve never ran into the same thing before.
z
What I have done now is declare an extension copy method in Animal interface that simulates what I want to do, but the implementation is ugly:
Copy code
fun Animal.copy(color: Color = this.color): Animal {
    return when (this) {
        is Sheep -> copy(color = color)
        is Dog -> copy(color = color)
        is Cat -> copy(color = color)
        else -> throw RuntimeException("Unknown subclass of class ${Animal::class.java.simpleName}")
    }
}
Ofc Animal would have more field properties and so this copy extension also has more parameters. But thats the idea. I feel since all subclasses of Animal are data classes, there should be a way to do this without this ugly extension
a
What you are looking for, is actually sealed classes.
👆 1