我有一个字符串列表,如:
List<String> locations = Arrays.asList("US:5423","US:6321","CA:1326","AU:5631");
我想像这样在Map<String, List<String>>
中进行转换
AU = [5631]
CA = [1326]
US = [5423, 6321]
我已经尝试了这段代码并且可以正常工作,但是在这种情况下,我必须创建一个新的类GeoLocation.java
。
List<String> locations=Arrays.asList("US:5423", "US:6321", "CA:1326", "AU:5631");
Map<String, List<String>> locationMap = locations
.stream()
.map(s -> new GeoLocation(s.split(":")[0], s.split(":")[1]))
.collect(
Collectors.groupingBy(GeoLocation::getCountry,
Collectors.mapping(GeoLocation::getLocation, Collectors.toList()))
);
locationMap.forEach((key, value) -> System.out.println(key + " = " + value));
GeoLocation.java
private class GeoLocation {
private String country;
private String location;
public GeoLocation(String country, String location) {
this.country = country;
this.location = location;
}
public String getCountry() {
return country;
}
public void setCountry(String country) {
this.country = country;
}
public String getLocation() {
return location;
}
public void setLocation(String location) {
this.location = location;
}
}
但是我想知道,有什么方法可以在不引入新类的情况下将String
转换为Map<String, List<String>>
。
答案 0 :(得分:21)
您可以这样做:
df <- structure(list(a = c("ABC,SZY", "XYZ", NA, NA, "ABC,BNM,JKL",
"DEF", "XCV"), b = c("SZY", "XYZ,IOP", "QWE", NA, "BNM,JKL,STU",
"DEF", "HJK")), row.names = c(NA, -7L), class = "data.frame")
一种更好的方法,
Map<String, List<String>> locationMap = locations.stream()
.map(s -> s.split(":"))
.collect(Collectors.groupingBy(a -> a[0],
Collectors.mapping(a -> a[1], Collectors.toList())));
更新
根据以下评论,可以将其进一步简化为
private static final Pattern DELIMITER = Pattern.compile(":");
Map<String, List<String>> locationMap = locations.stream()
.map(s -> DELIMITER.splitAsStream(s).toArray(String[]::new))
.collect(Collectors.groupingBy(a -> a[0],
Collectors.mapping(a -> a[1], Collectors.toList())));
答案 1 :(得分:3)
尝试一下
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "MM/yyyy"
let enteredDate = dateFormatter.date(from: expiryDate.text!)
//Also convert the current date in the entered date format and then checks that the date is valid if enteredDate month or year is greater than current date.
let currentDate = dateFormatter.date(from: dateFormatter.string(from: Date()))
if enteredDate.compare(now) != ComparisonResult.orderedAscending {
print("Valid")
} else {
print("Not Valid")
}
答案 2 :(得分:3)
您只需将代码按部分分组即可,将第一组作为键,第二组作为值,而不是先映射
Map<String, List<String>> locationMap = locations
.stream()
.map(s -> s.split(":"))
.collect( Collectors.groupingBy( s -> s[0], Collectors.mapping( s-> s[1], Collectors.toList() ) ) );
答案 3 :(得分:2)
POJO呢?与流相比,看起来并不复杂。
public static Map<String, Set<String>> groupByCountry(List<String> locations) {
Map<String, Set<String>> map = new HashMap<>();
locations.forEach(location -> {
String[] parts = location.split(":");
map.compute(parts[0], (country, codes) -> {
codes = codes == null ? new HashSet<>() : codes;
codes.add(parts[1]);
return codes;
});
});
return map;
}
答案 4 :(得分:1)
似乎您的位置图需要根据键进行排序,您可以尝试以下操作
List<String> locations = Arrays.asList("US:5423", "US:6321", "CA:1326", "AU:5631");
Map<String, List<String>> locationMap = locations.stream().map(str -> str.split(":"))
.collect(() -> new TreeMap<String, List<String>>(), (map, parts) -> {
if (map.get(parts[0]) == null) {
List<String> list = new ArrayList<>();
list.add(parts[1]);
map.put(parts[0], list);
} else {
map.get(parts[0]).add(parts[1]);
}
}, (map1, map2) -> {
map1.putAll(map2);
});
System.out.println(locationMap); // this outputs {AU=[5631], CA=[1326], US=[5423, 6321]}