关于Java同步的问题

bet*_*oys 12 java synchronization

Java文档说"同一个对象上的两个同步方法的调用不可能交错".我需要知道的是,synchronized是否还会阻止同一类的两个不同实例中的同步方法进行交错.

例如,类Worker具有名为process()的方法.我们有几个Worker在自己的线程中运行的实例.我们希望防止同时运行process()方法的多个实例.会同步吗?

谢谢.

Aas*_*set 28

没有; synchronized仅防止多个线程在同一实例中同时执行该方法.如果您有n个实例,则可能有n个线程,每个线程在其中一个实例中执行该方法.

如果您需要确保只有一个线程可以跨所有实例执行该方法,您应该创建该方法static,或者使该方法synchronized不是,而是使用synchronized方法内的块来锁定private static字段.

编辑:请注意,在private实例变量上进行同步更适合使用synchronized方法或进行同步this,并且锁定private static实例变量更适合具有static synchronized同步的方法或实例方法this.getClass().原因是this并且this.getClass()是整个程序都可以访问的对象引用,因此任何人都可以在这些对象上进行同步,从而阻止想要调用方法的线程.

编辑:另外,请参阅下面的@Cugan的评论 - 摘要:如果你真的想要锁定类,你可能想要使用synchronized (Worker.class)而不是synchronized (this.getClass()),取决于在子类化的情况下你想要的效果.

  • 更重要的是,你不应该在`this.getClass()`上同步另一个原因 - 它不会在继承的情况下工作!如果类Worker有两个子类,FooWorker和BarWorker,那么在FooWorker实例与BarWorker实例上调用时,.process()的调用将采用不同的锁.同意`private static`变量是一个更好的主意,但如果你想在类上同步,那就明确:`synchronized(Worker.class)` (5认同)