Java布尔值在定义后返回null

时间:2014-03-06 01:08:36

标签: java nullpointerexception

在查看了类似的其他多个问题之后,我似乎仍然遇到了这个问题。 This似乎是唯一的相关职位,但它仍然没有回答我的问题。我遇到的问题是在我的main函数中我建立了一个布尔值,但是在一个函数中我调用之后它给了我一个NPE。如图所示:

public class Display extends JFrame {
private static final long serialVersionUID = 1L;

public JPanel gp = (JPanel) getGlassPane();
public Images i;
public ActualGameClass p;
public Draw d;
public Controls c;
public boolean AllLoaded = false;

public Display(){
    i = new Images();
    gp.setVisible(true);
    c = new Controls(this, d);
    c.loadControls();
    p = new ActualGameClass();
    d = new Draw(p, i);
    i.loadImages();
    System.out.println(c.ControlsLoaded);
    AllLoaded = true;
    gp.setLayout(new GridLayout(1, 1, 0, 0));
    this.setLayout(new GridLayout(1, 1, 0, 0));

    gp.add(d, p);
    this.add(i);
    p.Game();
}

然后在类ActualGameClass.java

public void Game(){
    if(Main.f.AllLoaded){
    //game
    }
}

当我运行此代码时,它指向

if(Main.f.AllLoaded)

说有一个NPE。

因为它已被请求,我在评论中遇到格式化问题: Main就是我用来在JFrame中设置窗口的相关类

public class Main {

public static Display f = new Display();
public static int w =
        Main.f.ResChoiceW + 0;
public static int h = 
        Main.f.ResChoiceH +22; //Top Bar of GP renders as 22px
public static void main(String args[]){
    f.setSize(w, h);
    f.setResizable(false);
    f.setVisible(true);
    f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    f.setTitle("Eddy's Adventures");
    f.setLocationRelativeTo(null);
    f.setAlwaysOnTop(false);
}

和Stacktrace

Exception in thread "main" java.lang.ExceptionInInitializerError
    Caused by: java.lang.NullPointerException
        at com.fireFlower.pasterino.ActualGameClass.Game(ActualGameClass.java:24)
        at com.fireFlower.pasterino.Display.<init>(Display.java:31)
        at com.fireFlower.pasterino.Main.<clinit>(Main.java:7)

2 个答案:

答案 0 :(得分:4)

因为您在p.Game();构造函数的内运行了Display 并且引用了一个也在Display的构造函数中分配的变量,所以引用一个未完全构造的Display对象。

这有助于理解:http://vlkan.com/blog/post/2014/02/14/java-safe-publication/

答案 1 :(得分:0)

继续@ JustinJasmann的回答:

  1. 取消对p.Game()构造函数中Display的调用。除非你真的知道你在做什么,否则应该避免递归调用。

  2. 完全删除AllLoaded变量

  3. void Game()更改为void Game(Display disp)

  4. 作为您主要的最后一行(我认为),请致电Game(f)

  5. 考虑将变量命名为更能说明它们的含义,并遵循命名约定:

    f         --> disp
    void Game --> void startGame   //Functions should start with lowercase.
    w         --> resNum  ??
    h         --> resNumH
    

    等等。