Java 阻止其他操作的线程

Java 阻止其他操作的线程,java,synchronization,Java,Synchronization,我有一个例子,一个项目中有5个线程,比如a、B、C、D和X 定期触发线程X以调用methodX()并更新对象。 我希望A、B、C和D都是块,而X正在调用一个方法methodX(); 否则,A、B、C和D将继续,而不会互相等待。 假设A、B、C和D调用相同的方法,methodCommon() 我如何实施这样的案例?使用同步锁和重入锁不适合这种情况。您有两个基本选项: 使用捕获中断异常的try catch块将工作代码包装在线程A-D中(methodCommon())。当X使用methodX()完成时

我有一个例子,一个项目中有5个线程,比如a、B、C、D和X

定期触发线程X以调用
methodX()
并更新对象。 我希望A、B、C和D都是块,而X正在调用一个方法
methodX()
; 否则,A、B、C和D将继续,而不会互相等待。 假设A、B、C和D调用相同的方法,
methodCommon()


我如何实施这样的案例?使用同步锁和重入锁不适合这种情况。

您有两个基本选项:

  • 使用捕获
    中断异常的
    try catch
    块将工作代码包装在线程A-D中(
    methodCommon()
    )。当X使用
    methodX()
    完成时,
    catch
    块调用包含您希望A-D执行的工作的任何方法
  • 声明一个易失性的、同步的变量,X将使用该变量来标记a-D,a-D需要定期检查以确定它们是否应该做一些特殊的事情

  • 每种方法都有权衡。方法1可能导致A-D的数据不稳定(这取决于他们具体在做什么)。方法2可能会导致A-D做的工作比您预期的多一些,或者响应比snappy稍小一些,等等(同样,具体取决于这些线程正在做什么)。

    使用
    等待
    通知所有人
    ,尝试以下操作:

    public class ThreadLetter extends Thread{
    
    private Object trigger;
    
    public ThreadLetter(Object trigger, String name){
    this.trigger=trigger;
    super(name);
    }
    
    
    @Override
    public void run(){
    synchronized(trigger){
    
    try{
    trigger.wait();
    
    }catch(InterruptedException e){
    
    }
    //invoke whatever method needs to be invoked
    }
    }
    
    }
    
    线程X:

    public class ThreadX extends Thread{
    
    private Object trigger;
    
    
    public ThreadX(Object trigger){
    this.trigger=trigger;
    super("threadX");
    }
    
    @Override
    public void run(){
    synchronized(trigger){
    
    try{
    //invoke methodX
    
    trigger.notifyAll();
    
    }catch(InterruptedException e){
    
    }
    
    }
    }
    
    }
    
    Object trigger=new Object();
    
    ThreadLetter A=new ThreadLetter(trigger,"A");
    ThreadLetter B=new ThreadLetter(trigger,"B");
    ThreadLetter C=new ThreadLetter(trigger,"C");
    ThreadLetter D=new ThreadLetter(trigger,"D");
    
    ThreadX X=new ThreadX(trigger);
    
    X.start();
    
    A.start();
    B.start();
    C.start();
    D.start();
    
    主类:

    public class ThreadX extends Thread{
    
    private Object trigger;
    
    
    public ThreadX(Object trigger){
    this.trigger=trigger;
    super("threadX");
    }
    
    @Override
    public void run(){
    synchronized(trigger){
    
    try{
    //invoke methodX
    
    trigger.notifyAll();
    
    }catch(InterruptedException e){
    
    }
    
    }
    }
    
    }
    
    Object trigger=new Object();
    
    ThreadLetter A=new ThreadLetter(trigger,"A");
    ThreadLetter B=new ThreadLetter(trigger,"B");
    ThreadLetter C=new ThreadLetter(trigger,"C");
    ThreadLetter D=new ThreadLetter(trigger,"D");
    
    ThreadX X=new ThreadX(trigger);
    
    X.start();
    
    A.start();
    B.start();
    C.start();
    D.start();
    

    ReentrantReadWriteLock
    解决您的问题:

    ReadWriteLock readWriteLock = new ReentrantReadWriteLock();
    Lock readLock = readWriteLock.readLock();
    Lock writelock = readWriteLock.writeLock(); 
    

    在A、B、C、D中使用
    readLock
    ,在X中使用
    writeLock
    使用A。我很好奇你对这个问题的理解是什么。听起来像是一个简单的读/写场景。我看不出你的建议有什么关系。我可以问你同样的问题。除了线程X更新一个对象所暗示的内容之外,你如何从一个没有提到读或写的问题中获得“读/写场景”呢?我的意思是,X是a-D的独占对象,而a-D之间并不是互斥的。这是一个经典的读/写锁定场景,与实际操作无关;我只知道A-D必须继续工作,直到X通知他们中的任何人/所有人其他重要的事情。如果他们试图访问与X共享的对象,A-D是否应该阻止也不明显。@shmosel总结了这个问题,谢谢。X对A-D是独占的,A-D之间不是独占的。如果ThreadX不运行,其他线程将保持等待状态,这不是我想要的