簡體   English   中英

具有等待和通知功能的Java多線程

[英]Java multithreading with wait and notify

我有這段代碼

public MultiThreadedSum(ArrayBuffer ArrayBufferInst)
{
    this.ArrayBufferInst = ArrayBufferInst;
    Sum = 0;
    Flag = false;
    StopFlag = false;
}

public synchronized void Sum2Elements()
{

    while(Flag)
    {
        try {wait();}
        catch (InterruptedException e){}
    }

    Flag = true;

    if (StopFlag)
    {
        notifyAll();
        return;
    }

    System.out.println("Removing and adding 2 elements.");

    Sum = ArrayBufferInst.Sum2Elements();

    notifyAll();
}

public synchronized void InsertElement()
{

    while(!Flag)
    {
        try {wait();}
        catch (InterruptedException e){}
    }

    Flag = false;

    if (StopFlag)
    {
        notifyAll();
        return;
    }

    System.out.println("Inserting the sum.");

    ArrayBufferInst.InsertElement(Sum);

    if (ArrayBufferInst.RetunrSize() == 1)
    {
        StopFlag = true;
    }

    System.out.println(ArrayBufferInst);

    notifyAll();
}

如您所見,我首先將Flag設置為false,以便其中一個線程可以輸入Sum2Elements方法並將其更改為true,這樣,每個人都可以等待。

我知道在同步代碼中,只有一個線程可以執行其操作,在這里我有兩個同步方法,這是否意味着2個線程在每個notifyall之后都嘗試執行此方法?

如果是這樣,那么一個線程是否不可能輸入Sum2Elements,在另一線程進入InsertElement之前將標志更改為true,從而跳過while循環?

謝謝

只有一個線程可以持有對象的鎖。 然后只有那個線程可以在該對象上輸入同步方法。

但是,線程可以通過調用Object.wait()來釋放鎖而無需從方法中返回。

因此您的代碼看起來不錯!

does it mean that 2 threads are trying to conduct this methods after each notifyall? 
Ans : It is very much possible for two threads to be in two of your synchronized methods since you are calling wait().

is it not possible for one thread to enter Sum2Elements, change the flag to true before the other thread enters InsertElement, and by that skipping the while loop?
Ans : Yes this is possible again for the same reason specified above.

Only one thread can execute one of two method at a time because both are synchronized though order is undefined

就像我說的那樣,一個方法只能一次由一個線程執行,除非執行線程通過調用wait方法釋放lock ,而另一個線程獲得該lock並執行其他synchronized方法則使這兩個語句成為可能

鎖是在類的對象上獲得的,而不是在任何特定的同步方法上獲得的。 這兩種方法都是實例方法。 因此,如果一個線程輸入了對象的任何同步方法(A說),那么任何其他線程都無法輸入該對象的任何同步方法,直到運行線程未調用notifyAll()方法為止。 在那個階段,所有等待線程競爭成為活動線程,但是取決於線程調度器選擇要成為活動線程的線程。

如果希望兩個不同的線程同時訪問這些同步方法,則這兩個線程應在該類的2個不同對象上操作。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM