Java程序流程和OOP

Jak*_*son 5 java oop

我是一个Java新手,也是OOP的新手.我多年来一直是程序员,但现在正在努力学习OOP.当我通过在线Java课程时,我正在尝试编写一个基本的练习程序.这是一个跟踪人们游戏得分的程序.这就是我想要发生的事情:
1.询问用户的玩家数量.
2.询问球员的名字.
3.显示跟踪分数的主程序窗口.

我正在使用Swing.我的代码当前显示了上面#1的JTextField.我的想法是我在JTextField上放了一个ActionListenter,当用户点击进入时,它会获得/存储玩家的数量.这有效.但接下来的步骤是我遇到OOP问题.这是我的ActionListener的代码:

private class InputHandler implements ActionListener
{
    public void actionPerformed(ActionEvent e)
    {
        String enteredText = e.getActionCommand();
        numPlayers = Integer.parseInt(enteredText.trim());
    }
}
Run Code Online (Sandbox Code Playgroud)

因为我需要程序等到我有numPlayers,所以我决定实例化该类以获取ActionListener中的玩家名称.但是,由于此类是ActionListener,因此我可以/不能在那里做什么限制.我想要实例化的类称为GetPlayerNames,它只是一个扩展JFrame的公共类.我已经尝试将其置于actionPerformed(在InputHandler中):

GetPlayerNames temp = new GetPlayerNames(numPlayers);
Run Code Online (Sandbox Code Playgroud)

(我在这里使用"temp"因为我不需要对这个变量做任何事情......这只是我能让它工作的唯一方法),但当然这给了编译器警告,因为"temp"从未使用过.当然,这是一个混乱和糟糕的形式.救命?

小智 1

另外,由于 ActionListener 是一个嵌套类,因此它可以调用其父类中的方法:

public class Game {

    private void initUI() {
        // ...
        textField.addActionListener(new InputHandler());
        // ...
    }

    // ...

    private void showPlayerNameFrame(int numPlayers) {
        GetPlayerNames playerNameFrame = new GetPlayerNames(numPlayers);
        playerNameFrame.setVisible(true);
    }

    // ...

    private class InputHandler implements ActionListener {
        public void actionPerformed(ActionEvent e) {
            String enteredText = e.getActionCommand();
            int numPlayers = Integer.parseInt(enteredText.trim());
            showPlayerNameFrame(numPlayers);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这可以使您的代码更清晰,因为“拥有”逻辑的对象(在本例中为 Game 类)是执行实际操作的对象。

通常,动作侦听器只解析动作并将处理传递给类是有意义的。这是因为通常许多类型的侦听器可能会触发同一事件(例如值更改侦听器、操作侦听器、鼠标侦听器)

除了内部类之外,还可以使用匿名类

public class Game {

    private void initUI() {
        // ...
        textField.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                String enteredText = e.getActionCommand();
                int numPlayers = Integer.parseInt(enteredText.trim());
                showPlayerNameFrame(numPlayers);
            }
        });
        // ...
    }

    // ...

    private void showPlayerNameFrame(int numPlayers) {
        GetPlayerNames playerNameFrame = new GetPlayerNames(numPlayers);
        playerNameFrame.setVisible(true);
    }

    // ...
}
Run Code Online (Sandbox Code Playgroud)

使用 Java 8,您还可以使用Lambda方法引用而不是匿名类来实现相同的目的。

拉姆达:

public class Game {

    private void initUI() {
        // ...
        textField.addActionListener(e -> {
            String enteredText = e.getActionCommand();
            int numPlayers = Integer.parseInt(enteredText.trim());
            showPlayerNameFrame(numPlayers);
        });
        // ...
    }

    // ...

    private void showPlayerNameFrame(int numPlayers) {
        GetPlayerNames playerNameFrame = new GetPlayerNames(numPlayers);
        playerNameFrame.setVisible(true);
    }

    // ...
}
Run Code Online (Sandbox Code Playgroud)

方法参考:

public class Game {

    private void initUI() {
        // ...
        textField.addActionListener(this::showPlayerNameFrame);
        // ...
    }

    // ...

    private void showPlayerNameFrame(ActionEvent e) {
        String enteredText = e.getActionCommand();
        int numPlayers = Integer.parseInt(enteredText.trim());
        showPlayerNameFrame(numPlayers);
    }

    private void showPlayerNameFrame(int numPlayers) {
        GetPlayerNames playerNameFrame = new GetPlayerNames(numPlayers);
        playerNameFrame.setVisible(true);
    }

    // ...
}
Run Code Online (Sandbox Code Playgroud)

在大多数情况下,就源代码的可维护性和可读性而言,方法引用可能是实现 ActionListener 的最佳方式。