If interface has 2 method A() And B() and abstract class has also same A() and B() then what
is the different between them?
An interface just provides a skeleton of a class which implements this interface.
A abstract class (which can implement an interface, too) can add some default functionality which (of course) can be overridden in derivated classes.
Take a look at: Interface vs Abstract Class (general OO)
The difference is that classes that implement the interface will be forced to provide their own implementation of these methods, while classes that extend the abstract class will be provided with an implementation of these methods.
Differences:
Assuming A() and B() don't have implementation in abstract class, i.e. only signatures.
In case of the interface A() and B() will only be signatures, i.e. without any implementation and class implementing this interface will have to provide the implementation like this (without keyword override):
returnType AbstractClass.A()
{
// Code here
}
A class implementing Abstract class will have to override the abstract methods like this:
override accessSpecifier returnType A()
{
// Code here
}
override accessSpecifier returnType B()
{
// Code here
}
Related
I have a class with a function like so:
#Component
class UpdateService(
private val storeGateway: UpdateStoreGateway,
private val loadGateway: UpdateLoadGateway,
private val updateNotify: UpdateNotify,
) : UpdateStorage {
override fun delete(key: UpdateKey) {
if (loadGateway.loadByKey(key) != null)
storeGateway.delete(key)
updateNotify.deleted()
}
}
}
UpdateStoreGateway, UpdateLoadGateway and UpdateNotify are Interfaces. Since I'm new to Kotlin I can't quite grasp how the method override fun delete(key: UpdateKey) knows which implementation of the methods to take since there is no mention of the implementation class.
It's implementing all three!
An interface requires that all implementing clases must provide method(s) with the required signature(s). (That is: having the required name, and taking the required parameter type(s).) But there are no restrictions on where that method is defined: it could be in the implementing class, or inherited from a superclass. And similarly, there are no restrictions on a method implementing more than one interface, if the signature matches.
All that matters is that users of the class know they can call the method(s) specified in all implemented interfaces; they shouldn't know or care about the details.
interface IA {
fun callMe()
}
abstract class AbstractA {
abstract fun callMe()
}
// Allowed
class ImplementationA(a: IA): IA by a
//Why this is Not Allowed ?
class ImplementationA(a: AbstractA): AbstractA() by a
I could not find any satisfactory reason on why Abstract class cannot be delegated using "by" keyword.
Note:
Saying that we need to call constructor of Abstract class while extending it , this is not a satisfactory technical answer for the problem.
It's impossible because delegating is limited to interfaces exclusively.
One of the main reasons is, let's say, breaking the contract - if a class is delegated, what with "default" methods, like toString, hashCode, equals - should they be delegated or not?
This question (Why only interfaces can be delegated to in Kotlin) explains why it that and what would be consequences of dropping this limitation.
If I have an interface, is there any easy way I can declare a function to make it a public member, but non-overridable? Meaning, it would be exclusively callable and could not be set or overridden by its descendants
interface IFoo {
fun ExecuteOnly(){
// Do Something
}
}
I read a book recently by CommonsWare where this situation was described.
and I quote it from there:
"... As a result, anything in an interface hierarchy is permanently open , until you start
implementing the interfaces in classes. If that is a problem — if you have some
function that you really want to mark as final — use abstract classes, not interfaces..."
You can define an extension function on the interface.
fun IFoo.executeOnly() {
}
It will still be possible for someone to define a member function with that name in a class implementing IFoo but the intention is quite clear. And anyway when using an object via a IFoo reference the IFoo extension will be chosen.
No, you cannot. That's not how Kotlin's interface is implemented.
You can use an abstract class instead
abstract class Foo {
fun executeOnly(){
// Do Something
}
}
Ofcourse You Can... Actually there is not much difference bw kotlin interfaces and abstract classes... simply add a body and a private modifier..
interface MyInterface {
fun triggerTakeMe(){
takeMe()
}
private fun takeMe(){
println("Taken")
}
}
class MyClass : MyInterface
fun main() {
val obj = MyClass()
obj.triggerTakeMe()
}
I have seen few similar questions, but none had explained why delegation is limited to interfaces?
Most of the time in practice we have something that has actually no interface at all, it is a class that implements nothing but provides some functionality or implements an abstract class.
Is there any fundamental limitation that forces this to be limited to interfaces or can we expect kotlin to have unrestricted delegation in the future?
This is especially useful if we want to extend functionality of a class using composition not inheritance.
class A {}
class B(val a: A) : A by a {}
When you delegate an interface, the class does still implement the interface. So for consistency, if you can delegate a class, it should work the same way. I.e.
class A(x: Int) {
fun foo() = x
}
class B(val a: A) : A by a {}
needs to compile to
class B(val a: A) : A {
override fun foo() = a.foo()
}
except this doesn't work:
foo isn't open and can't be overridden.
you need to call a constructor of A. class B(val a: A) : A(a.x) won't help either: x is not a member of A.
What about equals and hashCode: are they delegated? Either decision would lead to weird consequences.
Trait delegation is described in docs, and there are no questions. But what about class delegation?
class FrameWorkClass // Third party class we cannot modify
class MyDerivedFrameWorkClass(c:FrameWorkClass) : FrameWorkClass by c
What is the best way to achieve this without modifying FrameWorkClass? Obviously we are unable to make it implement our interface.
You can only delegate an interface to a variable that implements that interface. You cannot delegate directly to another class. As #Damian was pointing out; basically is simplified as:
interface Framework {}
class FrameWorkImpl: Framework {}
class MyDerivedFrameWorkClass(val fw: FrameWorkImpl) : Framework by fw {}
Or you can generically say:
class MyDerivedFrameWorkClass(val fw: Framework) : Framework by fw {}
to accept any implementation of the Framework interface and delegate to it, so FrameworkImpl and FrameworkHappyDays both work if they implement the Framework interface.
This is updated to current Kotlin, where trait has been renamed to interface
At the moment only traits can be delegated like this. If you have a class that you would like to delegate, I would simply take that class and extract a trait(interface) including all the methods you are interested in. Here is an example based on your code.
Imagine you have these classes:
class FrameWorkClass {
fun foo() {}
fun boo() {}
}
class MyDerivedFrameWorkClass(c:FrameWorkClass) : FrameWorkClass by c
It does not compile right? Let's say you are interested in foo()
trait FrameWorkTrait {
fun foo() {}
}
class FrameWorkClassImpl: FrameWorkTrait {
override fun foo() {}
fun boo() {}
}
class MyDerivedFrameWorkClass(c:FrameWorkTrait) : FrameWorkTrait by c
At least this is how I would do it.