Reputation: 81
I'm having some difficulty understanding abstract classes/interfaces and I was wondering if someone would be kind enough to help me with my understanding.
It is my understanding that an interface is a means of defining the functionality of an object(how to use it) without defining its implementation.
So for instance, take a TV as an example.
Many manufacturers make TVs. If we were to define an interface for a TV, it may have methods such as :
ChangeChannel, PowerOn, PowerOff, RaiseVolume etc.....
So the interface is the human -> machine interface (buttons, knobs etc) and the implementation is the 'black box' internals we are interfacing with.
So then, if we wrote some classes that inherited from TV such as PhilipsTV, SonyTV etc which defined their own implementations of the methods defined in TV, then those specific manufacturer TV objects would override the TV interface methods and also provide an implementation.
Therefore, if we wanted to pass a TV object to a function but we didn't know which specific manufacturer made the TV until runtime, we could have a function such as :
void doSomethingWithTV(TV telly){
telly.ChangeVolume(10);
}
and call it like so :
void main()
{
SonyTV t = new SonyTV;
doSomethingWithTV(t);
}
The internals of doSomethingWithTV would know what methods a TV has since it is inherits from TV interface, but we may pass in a SonyTV or a PhilipsTV etc at runtime and they would be treated the same.
Unfortunately I'm having great difficulty passing an interface type as a parameter as my compiler says :
cannot declare parameter 'telly' to be of abstract type 'TV' because the following virtual functions are pure within 'TV':
virtual void TV::changeVolume(int)
Please could someone tell me if I'm understanding the term 'interface' correctly and if so how should I direct my research in order that I can learn the nessesary skills to be able to implement a pattern such as I have outlined above.
Thanks in advance, Rick.
Upvotes: 0
Views: 133
Reputation: 31
This happens because your TV class has a pure virtual function. You can't instantiate a class with a pure virtual function. Any class with a pure virtual function is an abstract class. These classes can't exist on their own, they need to be derived from by for example a SonyTV. If this SonyTV has defines the pure virtual function, then it would work.
You're doSomethingWithTV() asks for a TV, you're compiler errors because this function can never receive a TV. It can however receive references to a TV or classes derived from TV.
More information: https://en.wikibooks.org/wiki/C%2B%2B_Programming/Classes/Abstract_Classes https://en.wikipedia.org/wiki/Virtual_function
Upvotes: 0
Reputation: 259
Yes, you're understanding of what is an interface is pretty clear.
But :
You must use interface types (Tv here) with a pointer.
So in your exemple it would be:
void doSomethingWithTV(TV* telly){
telly->ChangeVolume(10);
}
and
void main()
{
TV* t = new SonyTV;
doSomethingWithTV(t);
}
An interface is made to pass a kind of contract : if you want to inherit from me you must implement all the pure virtual functions that I contain. It's not meant to be instantiated.
As you said, the function to call will be determined at runtime, so the compiler would not know which code to call at compile time.
Upvotes: 0
Reputation: 385114
Yeah, that's all right, except for two observations:
main
must return int
, not void
TV
object into the function, but that can't work because an interface cannot be instantiated. If you instead pass a reference TV&
, const TV&
or pointer TV*
then this is instead a handle to the original object and, when you use a handle, polymorphism can take hold.Both of these points are explained in your C++ book, so simply continue to read it to the end.
Upvotes: 0
Reputation: 1
"Unfortunately I'm having great difficulty passing an interface type as a parameter as my compiler says : ..."
You cannot pass abstract interfaces by value, so you change
void doSomethingWithTV(TV telly){
telly.ChangeVolume(10);
}
to receive a reference or pointer parameter like this
void doSomethingWithTV(TV& telly);
or
void doSomethingWithTV(TV* telly);
The by value parameter requires you to have instances of TV
.
Upvotes: 3