2016-11-22 52 views
0

我正在使用BlueJ编写一个Java学校项目的游戏(在一个非常基础的层面上),我试图将一个包含大量信息的构造函数分成两个或三个单独的构造函数。最初的代码,我改变之前如下所示:Java中的几个构造函数

public class Game 

//fields omitted.. 
{ 
    public Game() //initialise game 
    { 
     createRooms(); 
    } 

    private void createRooms() // initialise rooms and exists and set start room. 
    { 
     Room bedRoom, kitchen; 

     bedRoom = new Room("in the bedroom"); 
     kitchen = new Room("in the kitchen"); 

     bedRoom.setExit("north", kitchen); 
     kitchen.setExit("south", bedRoom); 

     player = new Player(kitchen); 
    } 


    //Now, I want to seperate the contructor initialising the exits from the rest. 
    //I do so, by copying this to a new constructor below the createRooms constructor: 
    //initial code omitted.. 
    private void createRooms() // initialise rooms 
    { 
     Room bedRoom, kitchen; 

     bedRoom = new Room("in the bedroom"); 
     kitchen = new Room("in the kitchen"); 
    } 

    private void createExits() // initialise room exits and set start room. 
    { 
     Room bedRoom, kitchen; 

     bedRoom.setExit("north", kitchen); 
     kitchen.setExit("south", bedRoom); 

     player = new Player(kitchen); 
    } 
} 

当我编译,我得到了新的构造函数中的错误消息:“可变卧室可能没有被初始化”。我没有得到这个,因为变量是在前面的构造函数中初始化的。这可以从上面提供的信息和代码解决吗?提前致谢!

BR 新手。

+5

您的构造函数是一行。你怎么可能希望它更短? –

+1

你的每个函数都有一个单独的,完全不相关的变量。你想在课堂上有一个领域。 – SLaks

+0

你甚至没有一个真正的构造函数,它有任何参数。你想如何缩短它? – Grunzwanzling

回答

1

在您的代码中,bedRoom局部变量不是属性,因此当您声明它时需要为其指定一个值。目前,它是未初始化的,它甚至不会编译,因为如果它执行了,只要执行代码就会引发NullPointerException

如果您想初始化的构造,使他们到处可以看到里面的变量,声明他们为属性:

public class Game { 
    Room bedRoom; 
    Room kitchen; 
} 

而从其他方法删除这些行:

Room bedRoom, kitchen; 
+0

否;它是未初始化的,并且会给出编译器错误。 – SLaks

+0

@SLaks对,我重新回答了我的答案。 –

1

Constructores应该为每个final成员变量(在声明时不直接初始化)设置值。所以你想要的是不可能的。

您可以从某些成员变量中删除final关键字,但它们可能是null,这经常是个问题。

如果你的问题是,构造函数有许多参数,有(至少)2种常用的方法:

  1. 分割你的类的责任。
    你的班级很可能会做很多事情,你可以放一些代码来分开班级。很有可能你最终会得到一系列依次使用的类,这样每个类都只有很少的参数。

  2. 使用Builder模式
    与您共创,你必须为每个构造函数的参数单独二传手方法单独生成器类生成器模式。 这些设置方法通常会返回this(当前的Builder实例),以便可以调用链接。这样

    MyClass theObject = new MyClassBuilder().withA("the A").withB("the B") /*... */ .withZ("the Z").build();

    的方法,如果所有属性都给出build()检查,然后调用与许多参数的构造。

0

变量bedRoomkitchen具有本地范围,他们没有方法之外存在。你应该将它们声明为类成员。还有player

现在,当您将类成员初始化代码放入私有方法时,您应该考虑三次。为什么?因为可以在构建之后调用该方法,并且它将重置您的成员变量!我能想到的唯一原因是你有很多成员变量,并且构造函数变得非常长。

class Game { 
    private Room bedRoom; 
    private Room kitchen; 
    private Player player; 

    public Game() { 
     // And you should initialize class members directly in the 
     // constructor. Most of the time. 
     bedRoom = new Room("in the bedroom"); 
     kitchen = new Room("in the kitchen"); 
     player = new Player(kitchen); 

     connectRooms(); 
    } 

    private void connectRooms() { 
     bedRoom.setExit("north", kitchen); 
     kitchen.setExit("south", bedRoom); 
    } 
}