How to use Java regex or Java streams for the given string pattern and create a map out of it

会有一股神秘感。 提交于 2020-01-15 11:04:00

问题


I have a string with the following pattern,

String test = "name=ravi,age=30,id=1;name=teja,age=32,id=2";

As you can see above, ";" is used to separate persons and "," is used to separate person's attributes and "=" to map the values of those attributes.

I would like to convert the above string into a Map<String, Map<String, String>> where the key for the outer map is the id and the key for the inner map is the name.

Given that it is always guaranteed to have unique ids and names across the string, how do I achieve the requirement using Java regex or Java streams?

I could have done this using StringTokenizer or "split" method, but I would like to see if there is any other better way of doing this.

Edit: I have reached this far till now

List<String> persons =
                Arrays.asList(test.split(";"));

        List<List<String>> personAttribs =
                persons.stream().map(s -> Arrays.asList(s.split(","))).collect(Collectors.toList());

I am unable to take the personAttribs and convert that to the map I am looking for.


回答1:


Absolutely just for fun:

    Pattern p2 = Pattern.compile(",");
    Pattern p3 = Pattern.compile("=");
    String[] tokens = test.split(";");

    for (String token : tokens) {
        List<String> list = p2.splitAsStream(token)
                .flatMap(x -> p3.splitAsStream(x))
                .collect(Collectors.toList());

        result.put(list.get(5), IntStream.of(0, 2)
                .boxed()
                .collect(Collectors.toMap(list::get, x -> list.get(x + 1))));
    }

    System.out.println(result); // {1={name=ravi, age=30}, 2={name=teja, age=32}}

With java-9 this could be even nicer:

    Pattern p = Pattern.compile(";");
    Pattern p2 = Pattern.compile(",");
    Pattern p3 = Pattern.compile("=");

    List<String> list = p.splitAsStream(test)
            .flatMap(p2::splitAsStream)
            .flatMap(p3::splitAsStream)
            .collect(Collectors.toList());

    Map<String, Map<String, String>> result = IntStream.iterate(5, x -> x + 6)
            .limit(list.size() / 6)
            .boxed()
            .collect(Collectors.toMap(
                    list::get,
                    x -> Map.of(
                          list.get(x - 5), 
                          list.get(x - 4), 
                          list.get(x - 3), 
                          list.get(x - 2))));


来源:https://stackoverflow.com/questions/51827567/how-to-use-java-regex-or-java-streams-for-the-given-string-pattern-and-create-a

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!