Java 单件摆动组件

Java 单件摆动组件,java,swing,concurrency,singleton,event-dispatching,Java,Swing,Concurrency,Singleton,Event Dispatching,我正在开发一个swing应用程序,其中我有一个Factory类,该类提供组件,并将Singleton牢记在心。比如: public final class ComponentFactory { private static LibraryFrame libraryFrame; private static LibraryTableScrollPane libraryTableScrollPane; public static synchronized LibraryFr

我正在开发一个swing应用程序,其中我有一个Factory类,该类提供组件,并将Singleton牢记在心。比如:

public final class ComponentFactory {
    private static LibraryFrame libraryFrame;
    private static LibraryTableScrollPane libraryTableScrollPane;

    public static synchronized LibraryFrame getLibraryFrame() {
        if (libraryFrame == null) {
            libraryFrame = new LibraryFrame();
        }
        return libraryFrame;
    }

    public static synchronized LibraryTableScrollPane getLibraryTableScrollPane() {     
        if(libraryTableScrollPane == null) {
            libraryTableScrollPane = new LibraryTableScrollPane(getLibraryTable());
        }       
        return libraryTableScrollPane;
    }
}
我将此组件用作:

add(ComponentFactory.getLibraryTableScrollPane())
我还制作了一个ListenerFactory类,它提供了Swing/AWT的各种监听器

这种模式有缺陷吗?我可以将同一个组件或侦听器与两个同时可见的父组件一起使用吗


提前感谢。

除了单线程模式带来的耦合问题(=程序中的许多类依赖于工厂->如果工厂发生更改,系统的许多部分都会受到影响。)之外,单线程工厂应该在多线程环境中工作

但要小心不要优化它。有一种称为双重检查锁定(double checked locking)的技术,用于优化您的解决方案以获得更高程度的并发性,但它存在非常微妙的问题。如果您感兴趣,请参阅此声明(并注意签名人):


为了摆脱与工厂的耦合,我宁愿在一些顶级类中创建共享结构(表、侦听器、框架),这些顶级类也会创建需要引用这些结构的对象,并将结构传递给它们的构造函数。但这只是一个建议,我不知道程序的整体结构。

它有一个主要缺陷:它通过使每个组件都可以全局访问,从而导致缺乏封装。这会很快导致出现意大利面代码,其中每个对象都使用任何其他对象,而不是提供封装方法的依赖项的简短列表

实现的另一个问题是:同步是不必要的,因为Swing组件不是线程安全的,只能从事件分派线程使用。因此,您应该只让EDT调用您的方法,这使得同步变得不必要


最后,一个组件可能只有一个父组件。例如,如果同一组件必须在两个不同的帧中显示,则需要该组件的两个实例。

-1:Swing组件仅在一个线程中可用:EDT。OP的代码已经是线程安全的了。使用双重检查锁定只会使它更脆弱。如果你真的读了答案,你会发现我告诉他避免双重检查锁定。提示:“但小心不要优化它”、“……但它有非常微妙的问题”。没有任何东西可以阻止您从不同于EDT的线程修改Swing组件。请参阅:“如果从事件调度线程以外的任何线程修改Swing组件数据,则必须采取预防措施以确保数据完整性”。我不明白为什么答案应该被否决,但不管怎样……这篇文章是frm 2001,完全过时了。改为阅读:除非另有说明,否则所有Swing组件和相关类都必须在事件调度线程上访问。因此,这里有另一个链接(api链接在那里,所以我想它没有过时):“一些Swing组件方法在api规范中标记为“线程安全”;可以从任何线程安全地调用这些方法。”->没有一般规则。