如何使用数组列表作为字段有效地深度克隆对象数组
how to efficiently deep clone an array of objects with an arraylist as a field
最深元素:
class Player {
//fields contain:
int value;
}
收集于:
class Team {
//fields contain:
ArrayList<Player> players;
}
收集于:
class Splitter {
//fields contain:
Teams[] teams;
}
在 Splitter
的函数中,我必须克隆 teams
。我基本上必须通过克隆每个 Team
对象来克隆数组 teams
,每个对象都包含一个我必须克隆的 ArrayList players
。我不想自己克隆播放器对象。
到目前为止,我的解决方案如下所示:
private Team[] deepClone(Team[] teams) {
Team[] new_teams = new Team[teams.length];
for (int i = 0; i < teams.length; i++) {
new_teams[i] = new Team();
for (Player player : teams[i].getPlayers())
new_teams[i].getPlayers().add(player);
}
return new_teams;
}
有什么我可以更改以使其更高效或更优雅的吗?
您当前的解决方案相当于这个更简单的形式:
private Team[] deepClone(Team[] teams) {
Team[] new_teams = new Team[teams.length];
for (int i = 0; i < teams.length; i++) {
new_teams[i] = new Team();
new_teams[i].getPlayers().addAll(teams[i].getPlayers());
}
return new_teams;
}
您可以在没有循环索引的情况下使用流和 lambda 使它更优雅:
private Team[] deepClone(Team[] teams) {
return Stream.of(teams).map(team -> {
Team newTeam = new Team();
return newTeam.getPlayers().addAll(team.getPlayers());
}).toArray(Team[]::new);
}
理想情况下,如果你想进行完美的深度克隆,你也应该克隆玩家,我们应该始终在每个 class 中编写克隆方法,然后调用该克隆方法来获得克隆,无论如何你可以通过以下方式进行。
class Team {
//fields contain:
ArrayList<Player> players;
public Team clone() {
Team team = new Team();
team.players.addAll(players);
return team;
}
}
// ...
Team[] deepCloneTeams(Team[] teams) {
Team[] newTeams = new Team[teams.length];
for (int i = 0; i < teams.length; i++)
newTeams[i] = teams[i].clone();
return newTeams;
}
最深元素:
class Player {
//fields contain:
int value;
}
收集于:
class Team {
//fields contain:
ArrayList<Player> players;
}
收集于:
class Splitter {
//fields contain:
Teams[] teams;
}
在 Splitter
的函数中,我必须克隆 teams
。我基本上必须通过克隆每个 Team
对象来克隆数组 teams
,每个对象都包含一个我必须克隆的 ArrayList players
。我不想自己克隆播放器对象。
到目前为止,我的解决方案如下所示:
private Team[] deepClone(Team[] teams) {
Team[] new_teams = new Team[teams.length];
for (int i = 0; i < teams.length; i++) {
new_teams[i] = new Team();
for (Player player : teams[i].getPlayers())
new_teams[i].getPlayers().add(player);
}
return new_teams;
}
有什么我可以更改以使其更高效或更优雅的吗?
您当前的解决方案相当于这个更简单的形式:
private Team[] deepClone(Team[] teams) {
Team[] new_teams = new Team[teams.length];
for (int i = 0; i < teams.length; i++) {
new_teams[i] = new Team();
new_teams[i].getPlayers().addAll(teams[i].getPlayers());
}
return new_teams;
}
您可以在没有循环索引的情况下使用流和 lambda 使它更优雅:
private Team[] deepClone(Team[] teams) {
return Stream.of(teams).map(team -> {
Team newTeam = new Team();
return newTeam.getPlayers().addAll(team.getPlayers());
}).toArray(Team[]::new);
}
理想情况下,如果你想进行完美的深度克隆,你也应该克隆玩家,我们应该始终在每个 class 中编写克隆方法,然后调用该克隆方法来获得克隆,无论如何你可以通过以下方式进行。
class Team {
//fields contain:
ArrayList<Player> players;
public Team clone() {
Team team = new Team();
team.players.addAll(players);
return team;
}
}
// ...
Team[] deepCloneTeams(Team[] teams) {
Team[] newTeams = new Team[teams.length];
for (int i = 0; i < teams.length; i++)
newTeams[i] = teams[i].clone();
return newTeams;
}