Reputation: 5994
If got something like this:
public abstract class BaseFoo
{
public BaseFoo()
{
FooMethod();
}
public abstract void FooMethod();
}
public class Foo : BaseFoo
{
private Stream _stream;
public Foo(Stream stream)
{
_stream = stream;
}
public override void FooMethod()
{
//do anything with the stream
_stream.Read(...);
//--> _stream = null
}
}
As you can see. There is one big problem. The ctor of the BaseFoo class calls the abstract method FooMethod. In its implementation, it tries to access the _stream field. BUT _stream is null because the ctor of the Foo class was executed.
Is there any possibility or pattern, to solve that situation (I am able to change to base class). I am just searching for a nice solution.
Is there any possiblity to do something like that?
public Foo(Stream stream)
{
_stream = stream;
base();
}
Would be nice if anyone would have an idea.
Upvotes: 0
Views: 67
Reputation: 2857
When you are initializing a class that is inherited, you need to first initialise its base class as well. You would be able to see that easily if you change the constructor to have some parameters to accept (i.e. remove the default constructor):
public abstract class BaseFoo
{
public BaseFoo(bool testToDoSomething)
{
FooMethod();
}
public abstract void FooMethod();
}
In this case the code won't compile, because Foo class will say that BaseFoo doesn't contain parameterless constructor, which you need to call. Besides that this is not a purpose of a parameterless constructor.
I can think of a workaround, but it isn't too nice and you probably want to do it in a different way. But if you really don't, you can do something like:
public abstract class BaseFoo
{
private Action toRunOnConstruct;
public BaseFoo(Action toRunOnConstruct)
{
this.toRunOnConstruct = toRunOnConstruct;
toRunOnConstruct.Invoke();
}
}
public class Foo : BaseFoo
{
private Stream _stream;
public Foo(Stream stream) : base(()=> SomethingToDoWithTheStream(stream))
{
_stream = stream;
}
public static void SomethingToDoWithTheStream(Stream stream)
{
//do anything with the stream
stream.Read(...);
//--> _stream = null
}
Upvotes: 0
Reputation: 120450
Calling overridable methods from constructors is discouraged for precisely the reasons outlined in your question.
Call the FooMethod
method after construction is complete.
Upvotes: 2