我正在开发一个与蓝牙相机接口的安卓应用程序。对于存储在相机上的每个剪辑,我们将一些关于剪辑的字段(其中一些用户可以更改)存储在 XML 文件中。
目前,此应用程序是唯一将此 xml 数据写入设备的应用程序,但未来桌面应用程序或 iphone 应用程序也可能在此处写入数据。我不想假设另一个应用程序也不能有额外的字段(特别是如果他们有一个更新版本的应用程序添加了这个版本还不支持的新字段)。
所以我要防止出现这样一种情况:我们在另一个应用程序中向这个 XML 文件添加新字段,然后用户去使用 android 应用程序,它会清除其他字段,因为它不知道它们。
所以让我们举个假设的例子:
<data>
<title>My Title</title>
<date>12/24/2012</date>
<category>Blah</category>
</data>
当从设备读取时,这将被转换为一个看起来像这样的 Clip 对象(为简洁起见)
public class Clip {
public String title, category;
public Date date;
}
所以我使用 SAX 来解析数据并将其存储到剪辑中。我只是将字符存储在 StringBuilder 中,并在到达标题、类别和日期的结尾元素时将它们写出来。
我意识到,当我将这些数据写回设备时,如果原始文档中有任何其他标签,它们将不会被写入,因为我只写出我知道的字段。
这让我觉得也许 SAX 是错误的选择,也许我应该使用 DOM 或其他东西,这样我可以更容易地写出最初存在的任何其他元素。
或者我在想也许我的 Clip 类包含一些通用 XML 类型(可能是 DOM)的 ArrayList,并且在 startTag 我检查元素是否不是预定义的标签之一,如果是,直到我到达那个标签的末尾存储整个结构(但在什么?)..然后在写回时,我将浏览所有附加标签并将它们写到 xml 文件中(当然还有我知道的字段)
这是一个众所周知的解决方案的常见问题吗?
-- 2012 年 5 月 22 日更新 --
我没有提到在实际的 xml 中根节点(实际上称为注释),我们使用已设置为 1 的版本号。我短期内要做的是要求我的应用程序的版本号支持是 >= xml 数据的版本号。如果 xml 是一个更大的数字,我将尝试解析以读回,但会拒绝对模型进行任何保存。尽管如何做到这一点,我仍然对任何类型的工作示例感兴趣。
顺便说一句,我想到了另一个应该很容易的解决方案。我想我可以使用 XPATH 来查找我知道的节点,并在数据更新时替换这些节点的内容。但是,我运行了一些基准测试,当将 xml 解析到内存中时,解析 xml 的开销是荒谬的。只是没有进行任何查找的解析操作导致性能比 SAX 差 20 倍。使用 xpath 进行解析通常要慢 30-50 倍,考虑到我在列表视图中解析这些,这真的很糟糕。所以我的想法是让 SAX 将节点解析为剪辑,但将整个 XML 存储在 Clip 类的变量中(请记住,这个 xml 很短,小于 2kb)。然后,当我将数据写回时,我可以使用 XPATH 替换我在原始 XML 中知道的节点。
不过,仍然对任何其他解决方案感兴趣。除非它包含一些代码示例,否则我可能不会接受解决方案。