使用Java流将字符串列表转换为地图列表

时间:2018-08-14 07:34:19

标签: java java-8 java-stream

我有以下模式的字符串列表

String test ="name=john,age=28;name=paul,age=30;name=adam,age=50";
List<String> listOfStrings = Arrays.asList(test.split(";"));

我想将上述字符串列表转换为键值对映射列表(如下所示)。

[{name=john, age=28}, {name=paul, age=30}, {name=adam, age=50}]

上面的每个条目都列出了一个地图,其中键为名称,年龄和值为对应的值。

这是我为获得结果而做的事情。

listOfStrings.stream()
  .map(record -> Arrays.asList(record.split(",")).stream().map(field -> field.split("="))
  .collect(Collectors.toMap(keyValue -> keyValue[0].trim(), keyValue -> keyValue[1].trim())))
  .collect(Collectors.toList());

我想知道这是否有效,或者是否有更好的方法来使用Java流。

2 个答案:

答案 0 :(得分:3)

这是使用模式匹配的另一种方法,速度不如for循环,但比我的测量中的原始流解决方案快得多。

public static void main(String[] args) {
    String test ="name=john,age=28;name=paul,age=30;name=adam,age=50";
    String patternString = "(name)=(\\w*),(age)=(\\d*)[;]?";
    Pattern pattern = Pattern.compile(patternString);
    Matcher matcher = pattern.matcher(test);
    List<Map<String, String>> list = new ArrayList<>();

    while (matcher.find()) {
        Map<String, String> map = new HashMap<>();
        map.put(matcher.group(1), matcher.group(2));
        map.put(matcher.group(3), matcher.group(4));
        list.add(map);
    }
}

通过不匹配键(名称和年龄),而是在创建地图元素时对它们进行硬编码,可以稍微改善性能。

答案 1 :(得分:1)

如果您要表演,请放弃Stream API。特别是带有子流的流确实不利于编写高性能的应用程序。

以下是您的Stream API版本与普通的for循环的比较:

public static void main(String[] args) {
  final String test = "name=john,age=28;name=paul,age=30;name=adam,age=50";

  final List<Map<String, String>> result1 = loop(test);
  final List<Map<String, String>> result2 = stream(test);

  System.out.println(result1);
  System.out.println(result2);
}


private static List<Map<String, String>> loop(String str) {
  long start = System.nanoTime();

  List<Map<String, String>> result = new ArrayList<>();
  String[] persons = str.split(";");

  for (String person : persons) {
    String[] attributes = person.split(",");
    Map<String, String> attributeMapping = new HashMap<>();

    for (String attribute : attributes) {
      String[] attributeParts = attribute.split("=");

      attributeMapping.put(attributeParts[0], attributeParts[1]);
    }

    result.add(attributeMapping);
  }

  long end = System.nanoTime();
  System.out.printf("%d nano seconds\n", (end - start));

  return result;
}

private static List<Map<String, String>> stream(final String str) {
  long start = System.nanoTime();

  List<String> listOfStrings = Arrays.asList(str.split(";"));
  List<Map<String, String>> result = listOfStrings.stream()
    .map(record -> Arrays.asList(record.split(",")).stream().map(field -> field.split("="))
    .collect(Collectors.toMap(keyValue -> keyValue[0].trim(), keyValue -> keyValue[1].trim())))
    .collect(Collectors.toList());

  long end = System.nanoTime();

  System.out.printf("%d nano seconds\n", (end - start));

  return result;
}

支出:

  

183887纳秒

     

53722108纳秒

     

[{{name = john,age = 28},{name = paul,age = 30},{name = adam,age = 50}]

     

[{{name = john,age = 28},{name = paul,age = 30},{name = adam,age = 50}]