java - 在 Java 中处理未知数量的对象
问题描述
我在编程时经常遇到的一个问题是如何处理未知数量的对象。通过处理我的意思是引用它们,操纵它们等。至于我,这将是在开发较小的游戏和程序时。
目前我正在开发一个记分程序,它应该显示球员的姓名、他们的分数以及其他各种特征。此外,应该有两个按钮可以允许从得分表中添加和删除玩家,这就是我将在这里重点介绍的内容。它可能看起来像这样:
//A very limited version of my program
import java.awt.*;
import javax.swing.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
class Application extends JFrame implements ActionListener{
//Fields, variables and components
Container mainCont = getContentPane(); //Main container, the window itself
private JPanel buttonPanel;
private JPanel namePanel;
private JButton addPlayerButton;
private JButton removePlayerButton;
//...
//Many more components
public Application(){
//Basic window initiation
setTitle("Score Keeper");
this.setSize(650, 700);
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainCont.setBackground(Color.BLACK);
this.setContentPane(mainCont);
buttonPanel = new JPanel();
namePanel = new JPanel();
addPlayerButton = new JButton();
addPlayerButton.addActionListener(this);
buttonPanel.add(addPlayerButton);
removePlayerButton = new JButton();
removePlayerButton.addActionListener(this);
buttonPanel.add(removePlayerButton);
this.add(buttonPanel);
this.add(namePanel);
this.setVisible(true);
//Other code omitted for now
//Includes other graphic components, layout managers etc.
}
/*
* Action-Listener.
* Performs an event on an action.
*/
@Override
public void actionPerformed(ActionEvent event){
if(event.getSource() == addPlayerButton){
Application.Player newPlayer = this.new Player(); //Creates a new object, i.e. a new player
//See below for Player class
}
if(event.getSource() == removePlayerButton){
//******
// This is where the problem lies
}
}
//I use a nested class to create a new player
public class Player{
//Components etc.
private String name;
private JLabel nameLabel;
public Player(){
name = getName();
nameLabel = new JLabel(name);
namePanel.add(nameLabel);
}
public String getName(){
//This basically gets input from the user to assign a name to the new player
//Code omitted for now
}
}
}
到目前为止一切都很好。该程序基本上只有两个按钮,其中 addPlayerButton 添加了一个播放器对象,该播放器对象的名称显示在屏幕上。每次按下此按钮时,屏幕上都会添加一个新玩家。这可以无限次地进行。
当我们想要移除一个玩家时,问题就来了。我们怎么能做到这一点?我们不能通过名称引用它,因为所有玩家对象实际上都是匿名的。
当然,另一种选择是预先定义固定数量的玩家对象:
class Application extends JFrame implements ActionListener{
//Fields, variables and components
Container mainCont = getContentPane(); //Main container, the window itself
private JPanel buttonPanel;
private JPanel namePanel;
private JButton addPlayerButton;
private JButton removePlayerButton;
private Player player1;
private Player player2;
private Player player3;
//...
//Etc.
然后我们将能够直接寻址每个玩家对象,但这太不切实际了。我们不能添加超过预定义数量的玩家,如果我们想要更少的玩家,我们有一堆从未使用过的玩家对象。此外,我们必须对每个玩家的每次启动进行硬编码——每个 nameLabel 都必须手动添加到屏幕等。
请分享您如何处理此类问题以及如何处理未知数量的对象的知识。感谢您抽出宝贵的时间和帮助!
PS 我对这个论坛还是很陌生。请让我知道这个问题是否有什么我可以改变的等等。我做了我的研究,发现以前没有解决这个问题的问题,但如果有一个我错过了,请随时让我知道!
编辑1:好的。有很多很棒的答案。我选择了使用 hashmaps 作为正确的解决方案,因为我认为这是我提供的场所的最佳解决方案。我实际解决问题的方法是,我在播放器对象中添加了一个 JButton,它删除了存储在其中的播放器对象。我还放弃了为播放器使用嵌套类的概念,而是在单独的类中实现了它. 不过,我总体上学到的是,在处理对象并且您不知道对象的数量时,通常最好将它们存储在某种集合中。我的首选是 Hashmap,因为它提供了一种基于其属性(如字符串名称或类似名称)访问对象的简单方法。
解决方案
您可以使用 Map/Hashmap,每次创建玩家时,将其添加到地图中。
您还必须改变从直接在屏幕上绘制玩家,可能会更改为在地图中绘制所有玩家,这样当玩家从地图中移除时,它将不再被绘制。
你会做这样的事情:
Map<String, Player> map = new HashMap<>();
map.put(player.Name, player);
然后您将在该哈希图中绘制所有内容。要删除,您只需提供要删除的播放器的名称。
map.remove(player.Name);
当然,然后您会稍微更改代码以渲染地图内的所有内容,我相信您需要一种方法来知道要删除哪个玩家,您可能需要添加一个文本字段来输入要成为的玩家的名称删除。
推荐阅读
- usb - 通过usb协议连接两个fpga
- android - 如何将单节点 js api 用于移动应用程序(android/ios)和 web(模板引擎)?
- django - 在页面上使用 wagtailtrans 包时内容不显示
- wpf - 如何将提示添加到 MenuItem
- xcode - Xamarin.iOS 调试不起作用
- python - numpy asmatrix 有时会产生一个列表数组
- amazon-dynamodb - 带有 ctx.identity.username 的简单 GetItem 返回 null
- angular - Angular Organize mat-list by date
- azure-active-directory - 关于 ER 环境中 AAD 的端点
- css - How to changed normal nested css to styled-components?