Constructors of an abstract class shouldn't be public and they should be protected. My question is about methods in that abstract class. Can we declare them as public or they should be protected too for the same reason?
The justification for constructors on abstract types being protected is that there is simply no other entity that could call the constructor other than a derived type. Making the constructor public is meaningless in this case as it can't ever be invoked outside the type hierarchy. Hence the recommendation is to use protected as it's the most appropriate access modifier.
The same logic doesn't hold true with other members on the type. They can be freely invoked from outside the type hierarchy should their access modifier permit it.
public abstract class Dog {
// Public is appropriate here as any consumer of Dog could access
// Breed on an instantiated object
public abstract string Breed { get; }
// Public would be meaningless here. It's not legal to say
// 'new Dog' because 'Dog' is abstract. You can only say
// 'new Poodle' or 'new Bulldog'. Only derived types like
// Poodle or Bulldog could invoke the Dog constructor hence it's
// protected
protected Dog() { }
}
public class Poodle : Dog { }
public class Bulldog : Dog { }
Whether or not a particular member should be public or protected is highly dependent upon the particular API. The reasoning should be the exact same for abstract types as it is for non-abstract types
Abstract classes shouldn't have public constructors because they don't make sense. Abstract classes are incomplete, so allowing a public constructor (which anyone could call) wouldn't work as you can't instantiate an instance anyway.
Methods on abstract classes are another story. You can have implementation in an abstract class, which is the behavior that all subclasses will inherit. Think of a Shape class. Its purpose is to draw a shape on the screen, so it makes sense to make a Draw method public as you'll want callers to be able to ask your Shape to draw. The method itself can be abstract, forcing subclasses to implement, or possibly provide an implementation which may or may not allow overriding. It depends on what the defined behavior of your class should be.
It depends on your use case. If you want the methods of the abstract class visible to instances of your derived class, you should make them public. If, on the other hand, you want the methods visible only to your derived class, you should make them protected.
Related
The C# spec, section 10.1.1.1, states:
An abstract class is permitted (but
not required) to contain abstract
members.
This allows me to create classes like this:
public abstract class A
{
public void Main()
{
// it's full of logic!
}
}
Or even better:
public abstract class A
{
public virtual void Main() { }
}
public abstract class B : A
{
public override sealed void Main()
{
// it's full of logic!
}
}
This is really a concrete class; it's only abstract in so far as one can't instantiate it. For example, if I wanted to execute the logic in B.Main() I would have to first get an instance of B, which is impossible.
If inheritors don't actually have to provide implementation, then why call it abstract?
Put another way, why does C# allow an abstract class with only concrete members?
I should mention that I am already familiar with the intended functionality of abstract types and members.
Perhaps a good example is a common base class that provides shared properties and perhaps other members for derived classes, but does not represent a concrete object. For example:
public abstract class Pet
{
public string Name{get;set;}
}
public class Dog : Pet
{
public void Bark(){ ... }
}
All pets have names, but a pet itself is an abstract concept. An instance of a pet must be a dog or some other kind of animal.
The difference here is that instead of providing a method that should be overridden by implementors, the base class declares that all pets are composed of at least a Name property.
The idea is to force the implementor to derive from the class as it is intended to provide only a basis for a presumably more specialized implementation. So the base class, while not having any abstract members may only contain core methods an properties that can be used as a basis for extension.
For example:
public abstract class FourLeggedAnimal
{
public void Walk()
{
// most 4 legged animals walk the same (silly example, but it works)
}
public void Chew()
{
}
}
public class Dog : FourLeggedAnimal
{
public void Bark()
{
}
}
public class Cat : FourLeggedAnimal
{
public void Purr()
{
}
}
I think a slightly more accurate representation of your question would be: Why does C# allow an abstract class with only concrete members?
The answer: There's no good reason not to. Perhaps someone out there has some organizational structure where they like to have a noninstantiatable class at the top, even if a class below it just inherits and adds nothing. There's no good reason not to support that.
You said it -- because you can't instantiate it; it is meant to be a template only.
It is not "really a concrete class" if you declare it as abstract. That is available to you as a design choice.
That design choice may have to do with creating entities that are (at risk of mixing the terminology) abstractions of real-world objects, and with readability. You may want to declare parameters of type Car, but don't want objects to be declarable as Car -- you want every object of type Car to be instantiated as a Truck, Sedan, Coupe, or Roadster. The fact that Car doesn't require inheritors to add implementation does not detract from its value as an abstract version of its inheritors that cannot itself be instantiated.
Abstract means providing an abstraction of behaviour. For example Vehicle is an abstract form. It doesn't have any real world instance, but we can say that Vehicle has accelerating behaviour. More specifically Ford Ikon is a vehicle, and Yamaha FZ is a vehicle. Both these have accelerating behaviour.
If you now make this in the class form. Vehicle is abstract class with Acceleration method. While you may/ may not provide any abstract method. But the business need is that Vehicle should not be instantiated. Hence you make it abstract. The other two classes - Ikon and FZ are concrete classes deriving from Vehicle class. These two will have their own properties and behaviours.
With regards to usage, using abstract on a class declaration but having no abstract members is the same as having the class public but using protected on its constructors. Both force the class to be derived in order for it to be instantiated.
However, as far as self-documenting code goes, by marking the class abstract it informs others that this class is never meant to be instantiated on its own, even if it has no virtual or abstract members. Whereas protecting the constructors makes no such assertion.
The compiler does not prevent implementation-logic, but in your case I would simply omit abstract ?! BTW some methods could be implemented with { throw Exception("must inherit"); } and the compiler could not distinguish fully implemented classes and functions including only throw.
Here's a potential reason:
Layer Supertype
It's not uncommon for all the objects
in a layer to have methods you don't
want to have duplicated throughout the
system. You can move all of this
behavior into a common Layer
Supertype.
-- Martin Fowler
There's no reason to prevent having only concrete methods in an abstract class - it's just less common. The Layer Supertype is a case where this might make sense.
I see abstract classes serving two main purposes:
An incomplete class that must be specialized to provide some concrete service. Here, abstract members would be optional. The class would provide some services that the child classes can use and could define abstract members that it uses to provide its service, like in the Template Method Pattern. This type of abstract class is meant to create an inheritance hierarchy.
A class that only provides static utility methods. In this case, abstract members don't make sense at all. C# supports this notion with static classes, they are implicitly abstract and sealed. This can also be achieved with a sealed class with a private constructor.
If I have a project that contains similar classes and some may use the same implementation, but in most cases they implement their own way of handling the methods defined in an interface or abstract class. I am trying to figure out if an interface/abstract class is better or not. I don't get the point of an interface if you can just use an abstract class with virtual abstract methods.
Here is an interface:
public interface IAthlete
{
void Run();
}
Here is an abstract class:
public abstract class Athlete
{
public abstract void Run();
}
Here is an implementation of the interface:
public class Sprinter : IAthlete
{
public void Run()
{
Console.WriteLine("Running Fast....");
}
}
Here is an extension of the abstract class:
public class MarathonRunner : Athlete
{
public override void Run()
{
Console.Write("Jogging....");
}
}
Now if I decide to add a method called Stop to either the interface or abstract method, Sprinter and MarathonRunner both break and because I can provide some default implementation to abstract, it seems like a better choice. Am I missing something?
There are 2 main differences between Interfaces and abstract super-classes:
Abstract Classes
code reuse is possible by using an abstract super-class
you can only inherit one super-class
Interfaces
every method has to be implemented in each sub-class
a class can inherit more than 1 interface (multiple inheritance)
In the case where all you have is one piece of commonality to extract, you're quite right that there isn't a substantive difference between the two. But this is rather like saying "in the case of adding 1 to 2, there's no difference between an int and a double" - it's technically true, but not a particularly useful guide to how to think.
In case with any more complexity than this (that is, in most cases) there will be more classes, and pieces of common baheaviour to extract. Then you have to start making a significant choice between class inheritance and interface implementation, taking into account things like:
you only get one shot at choosing a base class, but you can implement as many interfaces as you like
if you want your 'parent' to do any work, it needs to be a class not an interface
and so on.
In general, the semantics of your classes should guide you - where the 'things' have an "IS A" relationship (like MarathonRunner to Athlete), inheritance is suggested; where the 'things' have an "I CAN FULFIL THE CONTRACT OF A" (like, say, Person to Runner), interface implementation is suggested.
Interfaces are a btter way to go as the current consensus amongst the .NET developer comunity is that you should favour composition over inheritance, so Interfaces are a much better strategy (think of Injection Containers and how usefull they are as well, and lets not get started on unit testing).
also, classes can implement many interfaces but can only inherit from one class (abstract or otherwise). also structs can implement interfaces but not inherit from another class.
At the runtime level, interfaces are more efficient as the runtime doesnt have to walk the inheritance stack in order to work out the polymorphic implications of calling a specific member.
Interfaces are a very useful feature, and are very similar to abstract classes, and in some circumstances, exchangable with abstract classes.
But, don't jump straight to interfaces, unleass you have to (very common antipattern in Java developers). I suggest, by reading your example, to stick to abstract classes.
Most of the times I only use interfaces, when I have several non related classes, and I need them to have common members, as If these classes came from the same base class.
In your example, you are trying to find what happen if you need a new stop method, when adding a base virtual method. These can be solved in a different approach, that is not Abstract Classes versus interfaces.
There are 3 choices:
(1) Add an abstract method that coerce the programmer to override it, in order to instantiate objects.
(2) Add a new virtual method that does something, but doesn't have to be overriden.
(3) Add a new method that does nothing, maybe applies to your case.
// cannot instantiate an abstract class
public abstract class Athlete
{
// helper method:
public /* non-abstract */ void DoNothing()
{
// does nothing on purpouse !!!
}
// (1) virtual & abstract method, must be overriden
public abstract void Run();
// (2) new virtual method, doesn't need to be overriden,
// but, maybe you dont like what it does
public virtual void Stop()
{
Message.Show("Stop !!!");
}
// (3) new virtual method, doesn't need to be overriden,
// its safe to be called
public virtual void TakeBreak()
{
// works like an abstract virtual method, but, you don't need to override
DoNothing();
}
} // class Athlete
// in a non abstract class, you must override all abstract methods
public /* non-abstract */ class Runner: Athlete
{
public override void Run()
{
DoNothing();
}
public override void Stop()
{
DoNothing();
}
// don't need to override this method
// public virtual void TakeBreak();
} // class Trekker
// ...
Runner ARunner = new Runner();
ARunner.Run();
ARunner.Stop();
ARunner.TakeBreak();
The third kind of virtual method, that may apply to your example, doesnt' have a special name, I already post a question about it on stackoverflow, but, nobody knew an special name for this case.
Cheers.
An important difference between interfaces and abstract classes is how their members handle multi-generational inheritance. Suppose there's an abstract class BaseFoo with abstract method Bar and interface IFoo with method Boz; class Foo inherits BaseFoo and implements IFoo, and class DerivedFoo inherits from Foo.
If DerivedFoo needs to override BaseFoo.Bar, it may do so, and its override may call base.Bar() if it needs to use its parent's implementation. If Foo implements Boz implicitly using a virtual method, then DerivedFoo may override that method and call base.Boz() (the override being a function of the class rather than the interface) but if Foo explicitly implements IFoo.Boz, then the only way for DerivedFoo to change the behavior of IFoo.Boz will be to re-implement it. If it does so, then Foo's implementation of IFoo.Boz will become inaccessible, even within DerivedFoo's implementation of the same interface member.
I would like to know the difference between two conventions:
Creating an abstract base class with an abstract method
which will be implemented later on the derived classes.
Creating an abstract base class without abstract methods
but adding the relevant method later on the level of the derived classes.
What is the difference?
Much like interfaces, abstract classes are designed to express a set of known operations for your types. Unlike interfaces however, abstract classes allow you to implement common/shared functionality that may be used by any derived type. E.g.:
public abstract class LoggerBase
{
public abstract void Write(object item);
protected virtual object FormatObject(object item)
{
return item;
}
}
In this really basic example above, I've essentially done two things:
Defined a contract that my derived types will conform to.
Provides some default functionality that could be overriden if required.
Given that I know that any derived type of LoggerBase will have a Write method, I can call that. The equivalent of the above as an interface could be:
public interface ILogger
{
void Write(object item);
}
As an abstract class, I can provide an additional service FormatObject which can optionally be overriden, say if I was writing a ConsoleLogger, e.g.:
public class ConsoleLogger : LoggerBase
{
public override void Write(object item)
{
Console.WriteLine(FormatObject(item));
}
}
By marking the FormatObject method as virtual, it means I can provide a shared implementation. I can also override it:
public class ConsoleLogger : LoggerBase
{
public override void Write(object item)
{
Console.WriteLine(FormatObject(item));
}
protected override object FormatObject(object item)
{
return item.ToString().ToUpper();
}
}
So, the key parts are:
abstract classes must be inherited.
abstract methods must be implemented in derived types.
virtual methods can be overriden in derived types.
In the second scenario, because you wouldn't be adding the functionality to the abstract base class, you couldn't call that method when dealing with an instance of the base class directly. E.g., if I implemented ConsoleLogger.WriteSomethingElse, I couldn't call it from LoggerBase.WriteSomethingElse.
The idea of putting abstract methods in a base class and then implementing them in subclasses is that you can then use the parent type instead of any specific subclass. For example say you want to sort an array. You can define the base class to be something like
abstract class Sorter {
public abstract Array sort(Array arr);
}
Then you can implement various algorithms such as quicksort, mergesort, heapsort in subclasses.
class QuickSorter {
public Array sort(Array arr) { ... }
}
class MergeSorter {
public Array sort(Array arr) { ... }
}
You create a sorting object by choosing an algorithm,
Sorter sorter = QuickSorter();
Now you can pass sorter around, without exposing the fact that under the hood it's a quicksort. To sort an array you say
Array sortedArray = sorter.sort(someArray);
In this way the details of the implementation (which algorithm you use) are decoupled from the interface to the object (the fact that it sorts an array).
One concrete advantage is that if at some point you want a different sorting algorithm then you can change QuickSort() to say MergeSort in this single line, without having to change it anywhere else. If you don't include a sort() method in the parent, you have to downcast to QuickSorter whenever calling sort(), and then changing the algorithm will be more difficult.
In the case 1) you can access those methods from the abstract base type without knowing the exact type (abstract methods are virtual methods).
The point of the abstract classes is usually to define some contract on the base class which is then implemented by the dervied classes (and in this context it is important to recognize that interfaces are sort of "pure abstract classes").
Uhm, well, the difference is that the base class would know about the former, and not about the latter.
In other words, with an abstract method in the base class, you can write code in other methods in the base class that call that abstract method.
Obviously, if the base class doesn't have those methods... you can't call them...
An abstract function can have no functionality. You're basically saying, any child class MUST give their own version of this method, however it's too general to even try to implement in the parent class. A virtual function, is basically saying look, here's the functionality that may or may not be good enough for the child class. So if it is good enough, use this method, if not, then override me, and provide your own functionality...
And of course, if you override a virtual method, you can always refer to the parent method by calling base.myVirtualMethod()
Okay, when you see a method like this:
A.Foo();
What you really have (behind the scenes) is a signature like this.
Foo(A x);
And when you call A.Foo() you're really calling Foo(this) where this is a reference to an object of type A.
Now, sometimes you'd like to have Foo(A|B|C|D...) where Foo is a method that can take either a type A, or B, or C, or D. But you don't want to worry about what type you're passing, you just want it to do something different based on the type that was passed in. Abstract methods let you do that, that's their only purpose.
I am surprised to know that an abstract class in C# is possible with no abstract methods also.
abstract class AbstractDemo
{
public void show()
{
Console.WriteLine("In Show Method");
}
}
class MainDemo:AbstractDemo
{
public static void Main()
{
Console.WriteLine("In Main Method");
}
}
Any explaination ?
Sometimes you don't want to give the possibility to instantiate a class but you need this class as a base class for other classes.
The reason for choosing abstract classes over interfaces is that you can provide some basic implementation.
This is entirely valid, and occasionally useful if you want to provide event-like behaviour: provide an abstract class with all the "event handlers" implemented as virtual methods with a default behaviour of doing nothing.
I've also personally used this a lot for abstract remote API client classes where all methods throw exceptions: they're abstract for the purposes of test doubles, expecting our implementations to be the only production implementations, but allowing users to create their own test doubles either by hand or via mocking frameworks. Making the methods virtual instead of abstract means that new RPCs can be added without that being a breaking change.
A derived class can then override some of the methods, but doesn't have to override any specific one, because nothing's abstract. It still makes sense for the class to be abstract because an instance of the base class would be pointless (as everything would be a no-op).
This pattern is much more common in Java than C#, however - as in C# you'd normally just use "proper" events.
An abstract class is a class that must be extended before it can be used. This does not it any way mean that the function themselves must be abstract.
Take for example an Animal class
public abstract class Animal
{
void Move()
{
//whatever
}
}
public class Fish : Animal
{
void Swim()
{
}
}
public class Dog : Animal
{
void Bark()
{
}
}
All animals can move but only the fish can swim and the dog can bark.
Or for a real life example. I have an Asp.net MVC base controller I use in my application. It has some basic methods I need very often like GetCurrentUser() and a function I wrote to help with localization. It also takes care of tracking so I don't have to rewrite that code in all of my controllers. The class has about 200 lines of code but not a single abstract method.
I think you're confusing abstract classes with interfaces. Interfaces can't have methods with body, abstract classes can. There are times when you want to prevent user from instantiating an object of a specific class; but still provide some base functionality for the classes that derive from it; this is what an abstract class is useful for.
If your class is just a base for other classes and it does not have an full usablility - in other words as a base itselfe is not usable at all then you want to prevent from creating instances of it. In this case you can make abstract class without abstract members.
You could use abstract keyword on a class just to signal the compiler that it can only used inheriting from it, and not directly; In this case you are not oblied to put abstract member on the class.
This is equivalent to put in the class only one protected constructor, but using abstract is more clear and understandable.
No better explanation than MSDN it self
http://msdn.microsoft.com/en-us/library/aa645615(v=VS.71).aspx
An abstract class cannot be instantiated directly, and it is a
compile-time error to use the new
operator on an abstract class. While
it is possible to have variables and
values whose compile-time types are
abstract, such variables and values
will necessarily either be null or
contain references to instances of
non-abstract classes derived from the
abstract types.
An abstract class is permitted (but not required) to contain abstract
members.
An abstract class cannot be sealed.
We have heard that in abstract class, there must be an abstarct member. But when I compile the abstarct class without an abstract method, it compiles. It gives me surprise. Now I am unable to find the article which explain exact behavior of an abstarct class.
using System;
namespace random
{
interface IHelper
{
void HelpMeNow();
}
public class Base : IHelper
{
public void HelpMeNow()
{
Console.WriteLine("Base.HelpMeNow()");
}
}
public class Derived : Base
{
public new void HelpMeNow() ///this line
{
Console.WriteLine("Derived.HelpMeNow()");
}
}
class Test
{
public static void Main()
{
Derived der = new Derived();
der.HelpMeNow();
IHelper helper = (IHelper)der;
helper.HelpMeNow();
Console.ReadLine();
}
}
}
the new keyword in the commented line is a little confusing for me. It jsut mean it overrides the implementation of method in base class.
Why not use override keyword?
It's not really overriding it, it's shadowing it. Given a reference to a Derived object, Base's HelpMeNow function will not be accessible1, and derivedObject.HelpMeNow() will call Derived's implementation.
This is not the same as overriding a virtual function, which HelpMeNow is not. If a Derived object is stored in a reference to a Base, or to an IHelper, then Base's HelpMeNow() will be called, and Derived's implementation will be inaccessible.
Derived derivedReference = new Derived();
Base baseReference = derivedReference;
IHelper helperReference = derivedReference;
derivedReference.HelpMeNow(); // outputs "Derived.HelpMeNow()"
baseReference.HelpMeNow(); // outputs "Base.HelpMeNow()"
helperReference.HelpMeNow(); // outputs "Base.HelpMeNow()"
Of course, if the above is not the desired behavior, and it's usually not, there are two possibilities. If you control Base, simply change HelpMeNow() to virtual, and override it in Derived instead of shadowing it. If you don't control Base, then you can at least fix it halfway, by reimplementing IHelper, like so:
class Derived : Base, IHelper{
public new void HelpMeNow(){Console.WriteLine("Derived.HelpMeNow()");}
void IHelper.HelpMeNow(){HelpMeNow();}
}
This version of Derived uses what's called explicit interface implementation, which allows you to satisfy the contract of implementing an interface without adding the implementation to your class's public interface. In this example, we already have an implementation in Derived's public interface that's inherited from Base, so we have to explicitly implement IHelper to change it2. In this example, we just forward the implementation of IHelper.HelpMeNow to our public interface, which is the shadow of Base's.
So with this change, a call to baseReference.HelpMeNow() still outputs "Base.HelpMeNow()", but a call to helperReference.HelpMeNow() will now output "Derived.HelpMeNow()". Not as good as changing Base's implementation to virtual, but as good as we're gonna get if we don't control Base.
1Exception: it is accessible from within methods of Derived, but only when qualified with base., as in base.HelpMeNow().
2Notice that we also have to declare IHelper as an interface the class implements, even though we inherit this declaration from Base.
In general, if interface IBase implements a member DoSomething, and IDerived inherits/implements Ibase, it expected that IDerived.DoSomething will be synonymous with IBase.DoSomething. In general, this is useful since it saves implementers of the class from having to provide redundant implementations. There are, however, some cases where a derived interface must implement a member which has the same name as a member in the base interface, but which will have to be implemented separately. The most common such situations are (1) the derived method will have a different return type from the base type, or (2) the base interface(s) implements a ReadOnly and/or WriteOnly property(s) with a certain and the derived type should implement a Read-Write property. For whatever reason, if interface IReadableFoo provides a read-only property Foo, IWritableFoo provides a write-only property Foo, and interface IMutableFoo simply inherits both, the compiler won't know whether a reference to Foo refers to IReadableFoo.Foo or IWritableFoo.Foo. Even though only IReadableFoo.Foo can be read, and only IWritableFoo.Foo can be written, neither vb.net nor C# can resolve the overload unless one implements a new read-write property Foo which handles both.