Java 8 Lambda表达式从操作事件匿名内部类中调用特定方法



我在JPanel上有一个文本字段,这个文本字段有一个Document Listener。由于文档监听器包含三个方法(removeUpdate、insertUpdate和changeUpdate),所以我如何使用Lambda表达式调用特定的方法。

    field.getDocument().addDocumentListener(new DocumentListener() {
        @Override
        public void removeUpdate(DocumentEvent arg0) {
            // TODO Auto-generated method stub
        }
        @Override
        public void insertUpdate(DocumentEvent arg0) {
            // TODO Auto-generated method stub
            button.setText(field.getText());
        }
        @Override
        public void changedUpdate(DocumentEvent arg0) {

        }
    });

如何使用类似field.getDocument().addDocumentListener(Lambda表达式)的Lambda表达式来调用此Document侦听器insertUpdate方法;

TL;DR:你不能。DocumentListener不是单一方法接口

为了使lambda充当特定interface的实例,interface必须具有单个抽象方法。

DocumentListener3abstract方法,因此您需要创建一个SMI,extends DocumentListener:

interface InsertListener extends DocumentListener {
    @Override
    default void removeUpdate(DocumentEvent e) {
    }
    @Override
    default void changedUpdate(DocumentEvent e) {
    }
}

现在您可以使用lambda表达式创建InsertListener的实例:

final InsertListener is = e -> button.setText(field.getText());

你可以将其转化为一种方法:

field.getDocument().addDocumentListener(is);

例如,您还可以创建一个interface,类似于:

interface InsertListener extends DocumentListener {
    void onEvent(DocumentEvent.EventType type, DocumentEvent e);
    @Override
    default void insertUpdate(DocumentEvent e) {
        onEvent(e.getType(), e);
    }
    @Override
    default void removeUpdate(DocumentEvent e) {
        onEvent(e.getType(), e);
    }
    @Override
    default void changedUpdate(DocumentEvent e) {
        onEvent(e.getType(), e);
    }
}

现在,您可以按类型处理任何事件:

final InsertListener is = (t, e) -> {
    if (t == DocumentEvent.EventType.INSERT) {
        button.setText(field.getText());
    }
};

这比匿名类稍微紧凑一些,但也不多。

最新更新