values of an instance variable is different in two

2019-09-09 05:38发布

问题:

I have a TurnIndicator class, and its method getTurn(); just returns String of "BLACK", "BLACK" and then alternates between "WHITE" and "BLACK".

Inside my Board class, which combines all classes in the package and make it work together, I created an instance of TurnIndicator class, _turn, and declared an instance variable _t with initial value _t = _turn.getTurn(); Then, I defined an accessor method for _t - getT().

Now, when I print the _t value inside the Board class, it prints "BLACK", "BLACK", and so on. However, when I access _t value using getT() in another class, SelectPieceListener, this prints null.

Why is it so?

I attach my class definitions below. Irrelevant parts are removed.

What I want to do eventually is depending on c == _st.checkMoveImpossible() condition, to make the game player choose between two options -

1. by clicking select button(in this case, _cmi becomes 1, and selectClicked() method do desired action for if(_cmi == 1) block. More specifically, it changes order of _t value, so that the player skips one turn), or

2. by clicking scroll button (in this case, _cmi becomes 2, and do similar thing in scrollClicked() method to let current player move the other player's piece.).

I made just the _cmi == 1 case action work, by putting everything inside selectClicked() method, but I had to provide _cmi==2 case(when the player clicked scroll button), so I had to decouple it from the method.

Now, I have been trying to make it work in SelectPieceListener class for now, so that I could move it to the Board class later if I succeed.

However, every attempt I made for hours failed. I have coded one class or two at a time, and this is my first time doing projects with many classes. I am really unexperienced at this kind of things.

If you could give me some advice, that will help me a lot.

I know this is really tedious work, but I may not be able to do this by myself.. Please spend some time to read the code and help me.

public class Board {
private Structure _st;
private TurnIndicator _turn;
private String _t;
private int _cmi;

public Board() {
    _turn = new TurnIndicator();
    _t = _turn.getTurn();
    _cmi = 0;   
}

public ScrollListener getScroll(){
    return _scroll;
}

public String getT() {
    return _t;
}
public int setcmi(int cmi) {
    return _cmi = cmi;
}

public void selectClicked(char dir) {
    int index = _scroll.getX();
    HNode<ArrayList<String>> current = _st.getPosition(index);
    System.out.println("checkMoveImpossible() = " + _st.checkMoveImpossible());
    System.out.println("_t in Board = " + _t);

    if(!current.getDatum().isEmpty()) {

        if(_t == current.getDatum().get(current.getDatum().size()-1) && _cmi == 0) {
            if(0 <= index && index < 17 && index != _st.indexOfSpBack()) {
                current.forward(_t, current.getDatum().size());
            }
            else if(17 <= index && index < 25) {
                char direction = dir;
                _st.start(current, direction);
            }
            else if(index == _st.indexOfSpBack()) {
                current.backward(_t, current.getDatum().size()-1);
            }

            _t = _turn.getTurn();
            System.out.println("turn is "+ _t);
            display();
        }


        else if(_t != current.getDatum().get(current.getDatum().size()-1) && _cmi == 0) {
            String s = _t == "WHITE" ? "BLACK" : "WHITE";
            System.out.println("It's "+_t+"'s turn now and only "
            +s+" can move this piece.");
        }

    }

    if(_cmi == 1) {
        _t = _turn.getTurn();
        _cmi = 0;
        System.out.println("_cmi if block is reached");
        display();
    }
    update();

}

below is the SelectPieceListener class definition

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;


public class SelectPieceListener implements ActionListener {
    private Board _board;
    private Structure _st;
    private String _t;

    public SelectPieceListener(Board board) {
        _board = board;
        _st = _board.getStructure();
        _t = _board.getT();
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        char c = _t == "WHITE" ? 'b' : 'w';
        _board.selectClicked('l');          
        System.out.println(_t);
        if(c == _st.checkMoveImpossible()) {
            String theOther = _t == "WHITE" ? "BLACK" : "WHITE";
            System.out.println("No possible move for "+_t+": click select to skip turn, " +
                    "or click scroll to move " + theOther + " pieces.");
            _board.setcmi(1);
            _board.update();
            _board.selectClicked('l');          
        }

    }
}

回答1:

Well,

I see you have some things I wouldn't recommend. The _t and _st fields in SelectPieceListener are not necessary as you can get them from the _board field, why keep duplicated references if it's not necessary?

On the other hand, I see you do a lot of String comparisions with ==, you should always use "STRING_LITERAL".equals(variable).

After that, I would recommend you to use an IDE like Eclipse so you can debug parts of your code. If your variable is null, it's probably getting lost at some point, a debugger will be the best way to find the issue.



回答2:

You have a problem in the Board constructor, the order should be changed:

public Board() {
    _turn = new TurnIndicator();   // <---- this goes first
    _t = _turn.getTurn();
    _cmi = 0;   
}


回答3:

public class Board {
    private Structure _st;
    private TurnIndicator _turn; //instance variable, null before initialization
    private String _t;
    private int _cmi;

    public Board() {
    _t = _turn.getTurn(); //_turn is null, so... how do you are not getting a NPE?
    _cmi = 0;   
}