简体   繁体   中英

How do I transfer a local variable between two classes?

I am writing a noughts and crosses code that can take console arguments to decide which strategy to use (different AI classes). If the user selects 'ultimatecomputerplayer' then this is implemented as p1/p2 depending in which order they input this and the other strategy (could be 'humanplayer' etc.) My problem is that the ultimate class needs to know which symbol it is, at the moment the game running class just assigns p1 to X and p2 to O but my ultimate class is written assuming it is X so this poses an issue.

This is the code that assigns the strategies and symbols:

NCGridV3 theGrid = new NCGridV3(gridSize, gridSize);
GameRunnerV3 theGame = new GameRunnerV3();
Scanner sc = new Scanner(System.in);

ArrayList <NCPlayer> ret = new ArrayList <NCPlayer>();

for (int i = 1; i < args.length; i++)
{
    switch (args[i])
    {
        case "RandomComputerPlayer":
            ret.add(new RandomComputerPlayer());
            break;

        case "SimpleComputerPlayer":
            ret.add(new SimpleComputerPlayer());
            break;

        case "UltimateComputerPlayer":
            ret.add(new UltimateComputerPlayer());
            break;

        case "HumanPlayer":
            ret.add(new HumanPlayer(sc, theGame));
            break;      
    }
}

NCPlayer p1 = ret.get(0);
NCPlayer p2 = ret.get(1);

p1.setMySymbol(SquareStatus.CROSS);
p2.setMySymbol(SquareStatus.NOUGHT);

I tried to assign the strategy's symbol like so:

public class UltimateComputerPlayer  extends GenericPlayer implements NCPlayer 
{       
    public UltimateComputerPlayer()
    {
        super();
    }

    @Override
    public GridCoordinate getNextMove(NCGridV3 currentGrid) 
    {
        SquareStatus symbol = GenericPlayer.getMySymbol();

But eclipse tells me I cant make a static reference to a non-static method.

Another option I tried was passing an integer into the UltimateComputer Class which would be 'i' from the loop in the game runner class, then having the symbol assign dependent on which place the class was called like so:

public UltimateComputerPlayer()
    {
        super();

        SquareStatus mysymbol;
        if (NC == 1)
            mysymbol = NCGridV3.SquareStatus.CROSS;
        if (NC == 2)
            mysymbol = NCGridV3.SquareStatus.NOUGHT;
    }

    @Override
    public GridCoordinate getNextMove(NCGridV3 currentGrid) 
    {
    .......

But this variable is not assigned in the GridCoordinate class and I dont know how to make it.

Any help is greatly appreciated, Thanks.

The second option can't work because NC is not defined (at least I can't tell where it would be) and also you assign the symbol to a local variable SquareStatus mysymbol in your constructor, which is gone as soon as you leave the constructor. You firstly have to make mysymbol an instance variable (by moving it above the constructor). Then you have the choice to either use the setter after construction or add the number to the constructor

class UltimateComputerPlayer {
    private SquareStatus mysymbol;

    public UltimateComputerPlayer(int nc) {
        super();


        if (nc == 1)
            mysymbol = NCGridV3.SquareStatus.CROSS;
        if (nc == 2)
            mysymbol = NCGridV3.SquareStatus.NOUGHT;
    }

    // [...]
}

However that seems to be a generic concept and should be moved up into the parent class. Also, I would avoid using magic numbers inside the class. Make the decision of what symbol to use outside the class and call the constructor with the symbol as parameter, rather than the number.

And as @VictorSorokin says, in your first solution, just call getMySymbol() instead of GenericPlayer.getMySymbol()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM