如何使用java流将列表转换为具有多个键和值的映射作为列表

sun*_*leo -1 java java-stream

我有 ssns 列表Users(id,ssn,name)和 ids 列表的列表,需要转换为 ssns 列表和 id 列表的映射。你能帮忙解决这个问题吗?

List.of(new User(1, "ssn1", "user1"), new User(2, "ssn2", "user2"), new User(3, "ssn3", "user3"))
Run Code Online (Sandbox Code Playgroud)
Map with 2 keys("SSNs","IDs") and list as value
"SSNs" -  List("ssn1","ssn2","ssn3")
"IDs" -  List(1,2,3)
Run Code Online (Sandbox Code Playgroud)

代码

public class Test {

    public static void main(String[] args) {

        List<User> users = List.of(new User(1, "ssn1", "user1"), new User(2, "ssn2", "user2"),
                new User(3, "ssn3", "user3"));

        Map<String, List<Object>> userMap = users.stream().collect(Collectors.groupingBy(User::getSsn));
    
    }

}

class User {
    public int getId() {
        return id;
    }

    public String getSsn() {
        return ssn;
    }

    public String getName() {
        return name;
    }

    int id;
    String ssn;
    String name;

    public User(int id, String ssn, String name) {
        this.id = id;
        this.ssn = ssn;
        this.name = name;
    }
}
Run Code Online (Sandbox Code Playgroud)

更新:更新List<User>List<Object>.

Hol*_*ger 7

它\xe2\x80\x99s 不一定是循环解决方案的改进,但您可以使用 Stream API 来解决该任务,如下所示:

\n
Map<String, List<Object>> result = users.stream()\n    .collect(Collectors.teeing(\n        Collectors.mapping(User::getId, Collectors.toList()),\n        Collectors.mapping(User::getSsn, Collectors.toList()),\n        (id, ssn) -> Map.of("IDs", id, "SSNs", ssn)));\n
Run Code Online (Sandbox Code Playgroud)\n

上面的例子适用于 Eclipse。看起来,javac 在类型推断方面存在问题。以下内容适用于两者:

\n
Map<String, List<Object>> result = users.stream()\n    .collect(Collectors.teeing(\n        Collectors.mapping(User::getId, Collectors.<Object>toList()),\n        Collectors.mapping(User::getSsn, Collectors.<Object>toList()),\n        (id, ssn) -> Map.of("IDs", id, "SSNs", ssn)));\n
Run Code Online (Sandbox Code Playgroud)\n

或者

\n
Map<String, List<?>> result = users.stream()\n    .collect(Collectors.teeing(\n        Collectors.mapping(User::getId, Collectors.toList()),\n        Collectors.mapping(User::getSsn, Collectors.toList()),\n        (id, ssn) -> Map.of("IDs", id, "SSNs", ssn)));\n
Run Code Online (Sandbox Code Playgroud)\n


YCF*_*F_L 6

一个简单的 for 循环可以解决您的问题,而不是使用流,我建议使用这个简单的可读解决方案:

Map<String, List<Object>> userMap = new HashMap<>();
userMap.put("SSNs", new ArrayList<>());
userMap.put("IDs", new ArrayList<>());
for (User user: users) {
    userMap.get("IDs").add(user.getId());
    userMap.get("SSNs").add(user.getSsn());
}
Run Code Online (Sandbox Code Playgroud)

结果

{IDs=[1, 2, 3], SSNs=[ssn1, ssn2, ssn3]}
Run Code Online (Sandbox Code Playgroud)