在庫のArrayListをファイルに永続化する分散システムを設計しています。ファイルにストックを書き込んでいますが、そのファイルを読み取ると、nullポインター例外エラーが発生します。
これはクラスAのフィールドです。
private static StockList instance = null;
これは、クラスAのgetInstance()メソッドで、ファイルから株式のリストを取得します。
public static StockList getInstance(){
if (instance==null){
try {
XMLDecoder d = new XMLDecoder(
new BufferedInputStream(
new FileInputStream("Stock.xml")));
instance = (StockList) d.readObject();
d.close();
} catch (IOException ex) {
instance= new StockList();
Logger.getLogger(StockList.class.getName()).log(Level.SEVERE, null, ex);
}
}
return instance;
}
これはクラスAコンストラクターであり、getInstance()にIOExceptionがある場合に呼び出されます。
public StockList(){
stock.put("APL", new Stock("APL","Apple","Apple",3200));
System.out.println("");
}
これは、クラスAのwriteStockListメソッドで、ストックをファイルに書き込みます。
public void writeStockList()
{
try {
XMLEncoder e = new XMLEncoder(
new BufferedOutputStream(
new FileOutputStream("Stock.xml")));
e.writeObject(getInstance());
e.flush();
e.close();
} catch (IOException ex) {
Logger.getLogger(StockList.class.getName()).log(Level.SEVERE, null, ex);
}
}
これは、サーバーの実行時にストックリストを初期化するクラスBの私のメインメソッドです。
public static void main(String[] args){
try {
//Make sure all lists are initialised
StockList.getInstance();
//delete after first run
//StockList.getInstance().addStock(new Stock("APL2","Apple2","Apple",3200));
//StockList.getInstance().writeStockList();
System.out.println(StockList.getInstance().getStock("APL" ).name);
System.out.println(StockList.getInstance().getStock("APL2" ).name);
System.out.println("registered ok");
} catch (RemoteException ex) {
Logger.getLogger(ClientServer.class.getName()).log(Level.SEVERE, null, ex);
}
System.out.println("finished server setup");
}
テストの目的で、プログラムを初めて実行するときは、次の行のコメントが解除されます。
//StockList.getInstance().addStock(new Stock("APL2","Apple2","Apple",3200));
//StockList.getInstance().writeStockList();
これにより、新しい在庫(APL2)がリストに追加され、ファイルに書き込まれます。
次の行は正しく印刷されています-両方の株が見つかったことを証明しています:
System.out.println(StockList.getInstance().getStock("APL" ).name);
System.out.println(StockList.getInstance().getStock("APL2" ).name);
次に、2回目の実行時に、上記の行がコメント化されますが、上記のSystem.out.printlnは次のエラーをスローします。
Exception in thread "main" java.lang.NullPointerException at food.stockticker.priceserver.ClientServer.main(ClientServer.java:46)
Java Result: 1
getInstance()が呼び出されたときに、2番目の項目がファイルに書き込まれ、ストックリストに読み戻されるため、上記は発生しないはずです。最初のアイテム(APL)を印刷すると、それが返されます。APL2を印刷すると、エラーが発生します。
Stock.xmlファイルが上書きされたか、最初の実行で行われた変更がxmlファイルに書き込まれなかったかのようです。何か案は?
編集:
XML:
<?xml version="1.0" encoding="UTF-8"?>
<java version="1.6.0_41" class="java.beans.XMLDecoder">
<object class="food.stockticker.priceserver.StockList"/>
</java>