java - 如何在 XML 文件中写入可序列化对象而不覆盖文件?SAXParseException
问题描述
正如标题所示,我想将对象写入文件而不覆盖同一个文件。问题是,当我尝试将对象写入文件时,我收到以下消息:
“org.xml.sax.SAXParseException;lineNumber:1;columnNumber:1;文件过早结束。继续……”
然后没有任何东西进入文件。如果我尝试在其他类型的文件(如 .ser)中进行可序列化,我会收到一条错误消息,指出无法写入文件。
package application.library.crud.kvlth;
import java.beans.XMLDecoder;
import java.beans.XMLEncoder;
import java.io.*;
import java.util.ArrayList;
import java.util.Scanner;
public class Create {
private static XMLEncoder output;
private static XMLDecoder inpt;
public static void main(String[] args) throws IOException {
openFile();
addRecords();
closeFile();
}
public static void openFile() {
try {
output = new XMLEncoder(
new BufferedOutputStream(
new FileOutputStream("library.xml")));
} catch (IOException ioException) {
System.err.println("Error opening file. Terminating.");
System.exit(1);
}
}
public static void addRecords() throws IOException {
inpt = new XMLDecoder(
new BufferedInputStream(
new FileInputStream("library.xml")));
ArrayList<Book> books;
Scanner input = new Scanner(System.in);
System.out.printf("%s%n%s%n? ",
"Enter ISBN number, Author's name, Book's Title.",
"Enter end-of-file indicator to end input.");
while (input.hasNext()) {
try {
Book record = new Book(input.nextLine(),
input.nextLine(), input.nextLine());
books = (ArrayList<Book>) inpt.readObject(); /*here
at my IDE (Intellij) it shows me the following
message: "Unchecked cast: 'java.lang.Object' to
'java.util.ArrayList'"*/
inpt.close();
books.add(record);
output.writeObject(books);
} catch (NullPointerException e){
e.getStackTrace();
} catch (ArrayIndexOutOfBoundsException arrayExc){
}
System.out.println("? ");
}
}
public static void closeFile() {
if (output != null)
output.close();
}
}
解决方案
没有办法write objects to the file without overwrite the same file
。如果要读取文件,请在中间插入一些元素,然后输出文件的其余部分,您要么必须在内存中读取它,然后再将其全部写出,要么写入您正在执行插入的临时文件和然后将临时文件复制到原始文件上。
因此,在您的情况下,将您的“输出”文件更改为临时文件,然后在完成输出后将其复制回原始文件。
流式处理示例: 例如,如果您的输入是 input.xml:
<books>
<Book>Genesis</Book>
<Bool>Leviticus</Book>
</books>
你会阅读元素,直到你想要添加一本新书,写入输出
read
<books>
write
<books>
read
<Book>Genesis</Book>
write
<Book>Genesis</Book>
然后附加您要添加的书
write
<Book>Exodus</Book>
然后继续剩下的
read
<Book>Leviticus</Book>
write
<Book>Leviticus</Book>
read
</books>
write
</books>
产生 output.xml:
<books>
<Book>Genesis</Book>
<Bool>Exodus</Book>
<Bool>Leviticus</Book>
</books>
使用 SAX 比将所有书籍包装在一个数组中要容易得多。除非您正在处理大量数据,否则您可能不需要这样做。
推荐阅读
- spring - Laravel guzzle post 请求创建功能不起作用(415 Unsupported Media Type`)
- python - 具有不同类型特征的数据集的分类
- python-3.x - 如何通过python3+在windows10平台安装PyV8?
- python - 使用 onefile 选项在 Pyinstaller 中添加数据文件
- php - 不同版本的php apcu
- c# - 计算图片框的点击次数,计算表单的点击次数,然后计算速率 winformapp c#
- neo4j - 将 Neo4j 数据库导出到 CytoScape
- wordpress - WordPress 网站下线,使用 Digital Ocean Droplet
- bash - 使用 CRON 运行脚本会出现语法错误
- javascript - localeCompare 排序时未检测到整数