【问题标题】:creating nested Json from array list multi map in java在java中从数组列表多映射创建嵌套Json
【发布时间】:2015-07-27 14:43:32
【问题描述】:

我有一个数组列表多图 -

ArrayListMultimap<String, String> fcmbuildProperties = ArrayListMultimap.create();
ArrayListMultimap<String, String> scm = ArrayListMultimap.create();
//HashMap<String, String> fcmbuildProperties= new HashMap<String, String>();
fcmbuildProperties.put("name", buildName);
fcmbuildProperties.put("timestamp", buildTimeStamp);
fcmbuildProperties.put("groupId", groupID);
fcmbuildProperties.put("artifactId", artifactID);
fcmbuildProperties.put("version", version);
fcmbuildProperties.put("environment", environment);
fcmbuildProperties.put("number", patch);
fcmbuildProperties.put("artifactPath", layoutPath);
fcmbuildProperties.put("architecture", architecture);
fcmbuildProperties.put("operatingSystem", operatingSystem);
scm.put("commit",commitSha);
scm.put("url", githubUrl);
scm.put("branch", githubBranch);

这显示为 json,如下所示:

{
  "operatingSystem": [
    "rhel5"
  ],
  "artifactPath": [
    "djin/platform/cache/test/rhel5/i386/packages/test/test-1.0.0-d.284.i386.rpm"
  ],
  "artifactId": [
    "test"
  ],
  "number": [
    "284"
  ],
  "architecture": [
    "i386"
  ],
  "url": [
    null
  ],
  "version": [
    "1.0.0"
  ],
  "timestamp": [
    "6/4/15/2015/11:22:7"
  ],
  "groupId": [
    "cache"
  ],
  "environment": [
    "snapshot"
  ],
  "commit": [
    null
  ],
  "name": [
    "fcm-dummy-web"
  ],
  "branch": [
    null
  ]
}

但我需要如何将其解析为:

{
    "name": "fcm-dummy-web",
    "url": "job/fcm-dummy-web/",
    "build": {
        "full_url": "job/fcm-dummy-web/29/",
        "number": 38,
        "url": "job/fcm-dummy-web/29/",
        "scm": {
            "url": "institutional/fcm-dummy-web",
            "branch": "origin/master",
            "commit": "989f0b78470f0dc9e262cc020e66837beef16c4e"
        },
        "artifacts": {
            "id": "test",
            "groupId": "djin/platform/cache",
            "operatingSystem": "rhel5",
            "environment": "snapshot",
            "path": "/cache/test/rhel5/i386/packages/testtest-1.0.0-d.269.i386.msi",
            "architecture": "i386",
            "version": "1.0.0"
        }
    }
}

所以嵌套的 json 比平面结构更多。什么是进行此操作的有效方法?

我用gson从arrayListMultimap中生成儿子:

Gson gson = new Gson();
String jsonString = gson.toJson(fcmbuildProperties.asMap()); 

【问题讨论】:

  • 什么是ArrayListMultiMap
  • 您希望它自动完成还是通过一一添加来创建 JSON?
  • ChetanKinger - 我相信你可以用谷歌搜索。 @DAO - 自动会很棒,或者我可以一一完成。
  • @Scooby, ArrayListMultiMap 不是标准类。请指定我们可以在哪里看到它。此外,您的代码会创建 scm 并在其中放入一些元素,但它从未附加到 fcmbuildProperties

标签: java json arraylist hashmap


【解决方案1】:

这取决于您用于 JSON 序列化的库。

许多图书馆都提供“漂亮的打印”,这是一个共同的属性:

Pretty printing JSON from Jackson 2.2's ObjectMapper

Pretty-Print JSON in Java

编辑:使用 Gson 很简单

Gson gson = new GsonBuilder().setPrettyPrinting().create();

在创建 Gson 对象时。

编辑 2:

public static class OuterObject {
    String name;
    String url;

    BuildProperties properties;

}

public static class BuildProperties {
    String full_url;
    int number;
    Map<String, String> scm = new HashMap<String, String>() {{
        put("url":"institutional/fcm-dummy-web");
        //etc
    }};

}

【讨论】:

  • 我用gson,反正是通过gson来做的?
  • 我想你对我想要的东西感到困惑,我不想要漂亮的印刷品。在我的示例中,我想要一个嵌套的 JSON 而不是扁平的 JSON。例如:我有扁平的键值对,我希望它们中的几个嵌套在 "Build" 下。我想知道一种简单的方法。
  • 抱歉,与其使用庞大的属性列表,不如围绕它创建一个 POJO?我会更新我的答案
  • 这不只是一个平面键值对吗?我在哪里引入嵌套?
  • @Scooby,你的问题很模糊。我也认为您不想打印漂亮,主要是因为第一个 json 在一行中,而第二个 json 打印得很漂亮。我不得不重新格式化它以查看它们具有不同的结构。请在提出问题时多做一些工作,不要太快投票否决答案。
【解决方案2】:

我假设 ArrayListMultiMap 来自 Google Guava 库。

如果是这样,您的代码不会构造深度结构化的对象,因此 GSON 也不会显示更深层次的结构。

一种方法是使用这样的法线贴图:

Map<String, Object> scm = new LinkedListMap<>();
scm.put("url", "institutional/fcm-dummy-web");
// TODO put the rest of the properties

Map<String, Object> artifacts = new LinkedListMap<>();
// TODO put the corresponding properties

Map<String, Object> build = new LinkedListMap<>();
// TODO put the props
build.put("scm", scm);
build.put("artifacts", artifacts);

Map<String, Object> root = new LinkedListMap<>();
root.put("name", "fcm-dummy-web");
root.put("url", "job/fcm-dummy-web/");
root.put("build", build);

现在您可以使用 GSON 打印此地图:

new GSON().toJson(root);

这里有几点需要注意: 1. 我们使用LinkedListMap 以便元素以与我们放置它们的顺序相同的顺序显示。您可以使用TreeMap 将它们改为按名称排序。使用普通的HashMap 也可以,但每次运行此代码时可能会得到不同的顺序。 2. 映射中的键是字符串,但有些值是字符串,有些是映射。所以我们必须使用 Map 从而失去类型检查。

很多时候更好的方法是为对象创建 POJO 类。这是一种方法:

public class BuildProperties {
    private String name;
    private Sting uri;
    private Build build;

    // TODO write getters and setters
}

public class Build {
    private String full_url;
    // ....
    private Scm scm;
    private Artifacts artifacts;

    // TODO write getters and setters
}

// TODO write the Scm and Artifacts classes

困扰我的一件事是工件部分。您的 JSON 仅用于一个工件。您可能需要它看起来像这样:

"artifacts": [
    {
        "id": "test",
        "groupId": "djin/platform/cache",
        "operatingSystem": "rhel5",
        "environment": "snapshot",
        "path": "/cache/test/rhel5/i386/packages/testtest-1.0.0-d.269.i386.msi",
        "architecture": "i386",
        "version": "1.0.0"
    }
]

要使用地图代码来获得它,您必须像这样更改它:

Map<String, Object> artifact1 = new LinkedListMap();
artifact1.put("id", "test");
// ...
List<Map<String, Object>> artifacts = new ArrayList<>();
artifacts.add(artifact1);

使用 POJO 代码,Build 类应如下所示:

public class Build {
    private String full_url;
    // ....
    private Scm scm;
    private List<Artifact> artifacts;

    // TODO write getters and setters
}

对于单个工件,该类应该是 Artifact

【讨论】:

    猜你喜欢
    • 2019-12-08
    • 1970-01-01
    • 2020-07-02
    • 2018-03-09
    • 2016-07-05
    • 1970-01-01
    • 2016-02-12
    • 2014-02-02
    相关资源
    最近更新 更多