Currently it’s proposed to avoid multiple class inheritance because of lack of it by design, instead use interfaces and delegates: class Foo : Bar by BarImpl()
But in this case you need to override methods in this BarImpl by some defaults first and then you have no any clue from a compiler that you need to override them again in the final class.
Also it provides a cascade boilerplate of overrides that doesn’t occur if you implement interfaces only. Besides, it’s not possible to pass a variable that should be only in a final class (e.g. this ).
It’s best to not to override these methods in the delegate and mark it as abstract.
I’m not sure what do you mean. Delegation in Kotlin is just a syntactic sugar to implement Delegation pattern more easily. And delegation pattern is related to the concept of composition over inheritance where we prefer to reuse the code by having several classes that talk to each other, instead of inheritance.
Kotlin didn’t invent delegation pattern and it doesn’t force it in any way. It provides tools to use this pattern easily.
Also, answering your another post that apparently was intended for this topic:
And answering many other your posts here.
No offence, but your attitude isn’t the best. You are clearly still learning, I think not only Kotlin, but programming in general. It is good you have a lot of questions, but they’re usually not like: “Why things were designed as they were?”, but more like: “Why it was designed wrong and when do you plan to fix this?”. And in many cases your suggestions are actually the opposite of what should be done.
I can assure you programming languages are not designed by 3 friends during a single evening. Designing takes months, a lot of discussion across several people, maybe even with the community. During that time many different possibilities are being analyzed, the team look at other languages to see what features could fit well into Kotlin, etc. I suspect most of your suggestions were either discussed already and they were rejected or they didn’t at all fit Kotlin and they weren’t even taken into consideration.
Consider that whenever you see something was designed badly, maybe in reality you just miss the context or experience to understand it fully.
Also, even generic-purpose languages (like Kotlin) have their specifics that you may like or not. From your posts it seems you would prefer a dynamic language that makes guesses on what do you need it to do. Kotlin is the opposite: strongly-typed, very strict and everything is rather explicit. But programming languages are just tools. You don’t have to use any specific language, you can choose one that suits you the best. (yeah, it is harder with Android).
Looks like it’s not a single dev’s problem https://youtrack.jetbrains.com/issue/KT-21955. What about multiple inheritance - can it solve it? Because as I said before, it’s even simpler to make an init method in interfaces instead of trying to fix overrides in delegates.
@Psijic can you give us a very concrete example where you needed this?
Delegation, imho, is not very useful in general.
But using delegation to somehow do mutiple inheritance is just … odd… what do you mean by “it’s proposed”?
Usually you can solve all your problems just using composition, have a few fields containing the classes to which you delegate/borrow code and explicilty implement all the methods from the interfaces you need.
That might be more verbose than some cool looking solutions, but it’s the cleanest: you specify in a single place how does your class behave.
All the “issues” with multiple ineritance are about how to combine classes which have implementation for their methods, and there’s no one-size-fits-all for that. The problem, if you wish, with multiple inheritance is not that there are no ways to make it work, is that there are too many, and different users need different things.
Delegation is a common alternative to multiple class inheritance. Instead of doing this:
open class BarkingAnimal {
fun bark() {
println("bark")
}
}
open class FlyingAnimal {
fun fly() {
println("fly")
}
}
class FlyingBarkingAnimal : FlyingAnimal(), BarkingAnimal() // not allowed
We do this:
interface BarkingAnimal {
fun bark()
}
interface FlyingAnimal {
fun fly()
}
open class BarkingAnimalImpl : BarkingAnimal {
override fun bark() {
println("bark")
}
}
open class FlyingAnimalImpl : FlyingAnimal {
override fun fly() {
println("fly")
}
}
class FlyingBarkingAnimalImpl : FlyingAnimal by FlyingAnimalImpl(), BarkingAnimal by BarkingAnimalImpl() // works
I personally definitely prefer the latter as it is much cleaner to me, although I don’t really use it in practice.
Try nested multiple inheritance. I have something like:
Interface B : C, E
Interface C
Interface E
Interface O: B
Interface G: W, E
Interface S: O, W
Interface W: B, E
abstract class Foo: B
final class Bar: Foo, W
final class Baz: Foo, G
final class Buzz: Foo, S
@broot i got that. But the resulting class is just the union of the 2 classes you delegate to, it has no state of its own.
There’s no difference wrt using the 2 impl classes.
@Psijic by concrete example i meant explain what do those classes do and why you need multiple inheritance.
But then you can’t delegate to it because you can’t create an instance of it.
I see your point on the limitation of the language, but I don’t see how it can be fixed at all.
In this specific example I would either try to rewrite the code in such a way that delegation isn’t necessary any more, or don’t make the delegate implement the interface, just some methods. Then create an instance of it and manually delegate to it. I certainly wouldn’t create empty boilerplate methods in a class just to use it as a delegate. That’s a code smell to me.