Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using 'this' in base constructor?

I'm working on a project that involves a lot of interfacing and inheritance, which are starting to get a little tricky, and now I've run into a problem.

I have an abstract class State which takes in a Game object as a constructor argument. In my Game class's constructor, it takes in a State. The idea is that when inheriting from the abstract base Game class, when calling the base class's constructor, you give it an initial State object. However this State object takes in the same Game that you're creating it in. The code looks like this:

public class PushGame : ManiaGame
{
     public PushGame() :
          base(GamePlatform.Windows, new PlayState(this), 60)
     {
     }
}

However this doesn't work. I can only assume because the 'this' keyword is not usable until after the constructor has begun to execute. Trying to use it in your base class's constructor doesn't work, apparently. So what would be my best workaround for this? My plan B is to just remove the State argument from the Game class's constructor and just set the state inside the constructor code afterwards.

Is there an easier, less-intrusive way of doing this?

like image 856
William Thomas Avatar asked Feb 26 '12 06:02

William Thomas


2 Answers

Clearly the ManiaGame class always uses objects of PlayState type, so you can move the creation at the ManiaGame level:

public class PushGame : ManiaGame
{
     public PushGame() : base()
     {
     }

}

public class ManiaGame
{
    PlayState ps;   
    public ManiaGame() {
        ps = new PlayState(this);
    }
}

If you want more concrete PlayState classes..

public class PushGame : ManiaGame
{
     public PushGame() : base()
     {
     }
     protected override PlayState CreatePlayState()
     {
        return new PushGamePlayState(this);
     }
}

public class ManiaGame
{
    PlayState ps;   
    public ManiaGame() {
          ps = CreatePlayState();
    }
    protected virtual PlayState CreatePlayState()
    {
        return new PlayState(this);
    }
}

public class PlayState
{
   public PlayState(ManiaGame mg) {}
}


public class PushGamePlayState : PlayState
{
   public PushGamePlayState(ManiaGame mg) : base(mg){}
}
like image 180
Adrian Iftode Avatar answered Sep 21 '22 21:09

Adrian Iftode


If the State implementation used depends on the concrete Game class, then I would create a new instance of the State inside the constructor of the child Game class (PushGame) and access the State in the base class through the abstract property.

public class PushGame : ManiaGame
{
    private readonly PlayState gamePlayState;

    public PushGame() : base()
    {
        gamePlayState = new PlayState(this);
    }

    protected override State GamePlayState
    {
        get { return gamePlayState; }
    }
}

public abstract class ManiaGame
{
    protected abstract State GamePlayState { get; }
}

public class State
{
    public State(ManiaGame mg) { }
}


public class PlayState : State
{
    public PlayState(ManiaGame mg) : base(mg) { }
}
like image 24
AlexD Avatar answered Sep 20 '22 21:09

AlexD