我们如何使用Java

时间:2018-07-30 13:07:40

标签: java json java-8

我正在从数据库中读取3列值(大约5万条记录),然后尝试在Json文件中搜索此值。 Json文件包含200万个Json对象。 我尝试了以下方法。

方法1。

JSONArray json = readJson(Constants.jsonFilePath);

private JSONArray readJson(String jsonFilePath) {
    String content = null;
    File file = new File(Constants.jsonFilePath);
    try {
        content = FileUtils.readFileToString(file, "utf-8");
    } catch (IOException e) {
        e.printStackTrace();
    }
    return new JSONArray(content);

}

然后线性搜索所需的字段值

我针对大小为150 MB的文件测试了上面的代码,效果很好。但是,当我针对大小为2 gb的文件进行测试时,却收到OutOfHeapMemory错误。

方法2:

然后,我尝试一次从文件中读取100 000个Json对象,然后检查所需的字段值,但是过程非常缓慢。

我正在使用org.json库。 有什么更好的方法来解决上述问题?

3 个答案:

答案 0 :(得分:4)

当然,它会很慢,它包含大量数据。 将其拆分为更多可管理的块是您唯一可以做的事情,并且您必须将对性能的影响作为经营的成本,因为它根本无法容纳在内存中。

当然,您可以告诉JVM声明4GB的RAM,并希望它足够了,但是处理该数量的数据仍然需要花费很多时间。

留下了一个问题,为什么您要尝试处理这么大的单个JSON对象,所以存储大数据的方法要比处理CPU和RAM少得多的方法好得多。 我想到了数据库,可以使用SQL或类似的查询语言很好地进行搜索。

在这一点上,您不仅正在运行合理的JVM限制,而且正在运行操作系统本身。

答案 1 :(得分:2)

您应该使用流式JSON解析器,而不是读取整个文件。 这将很慢,但是可以控制。 查看Jackson Streaming API,了解如何实现这一目标。

这确实意味着您将不得不处理JSON对象的低级处理,但是应该比将所有JSON加载到内存中更快。

此处link是使用Streaming API的地方。

请注意,GSON也具有类似的流API。

答案 2 :(得分:0)

您是否尝试过创建自己的JSON解析器(针对特定的JSON obj)?由于您已经知道这种情况下的JSON格式。然后只需线性解析单个obj(您可以使用readLine()直到第一个打开的'{')关闭'}'为止,然后与搜索值进行比较。 :D 您还可以使用多线程方法来减少时间。

这只是个主意,我仍然不清楚您的JSON文件是什么样子。