I have a thread subclass which represents arrivals at a public office and a thread subclass which represents the caseworkers.
Every time a person is arrived, the person's name is entered. There are 2 entrances for the office where the arrivals can enter their name. There can be no more than 10 persons in the waiting room. If there are more, they must wait until a place is available.
The caseworkers call the names that have been entered. There are 2 caseworkers. Of course, the names can only be called up if they have been entered and they is called in the order in which they have been entered (like a queue). When all the names are called up, the caseworkers must wait until more people arrive.
The threads for both the arrivals and the caseworkers sleep in a random number of seconds (from 1-10 seconds) every time.
I also have a common-class containing an arraylist with a list of names as a method and some methods for calling a name and entering a name. It also contains the append and take methods which is used to solve the problem (java's monitor).
Here is my code so far:
import java.util.Random;
public class ThreadClass_Arrivals extends Thread {
private CommonClass commonClass;
public int threadID;
public ThreadClass_Arrivals(CommonClass commonClass, int threadID) {
this.commonClass = commonClass;
this.threadID = threadID;
}
@Override
public void run() {
for (int i = 0; i < 20; i++) {
// time interval before a name is entered - the thread sleep between 1-10 seconds every time
Random random = new Random();
int randomNumber = random.nextInt(10) + 1;
int numberInThousand = randomNumber * 1000;
try {
Thread.sleep(numberInThousand);
} catch (InterruptedException e) {
e.printStackTrace();
}
commonClass.enterName(commonClass.namesList().get(commonClass.nameEnteredIndex), this.threadID);
// java monitor
commonClass.append((char) commonClass.nameEnteredIndex);
}
}
}
import java.util.Random;
public class ThreadClass_Caseworkers extends Thread {
private CommonClass commonClass;
public int threadID;
public ThreadClass_Caseworkers(CommonClass commonClass, int threadID) {
this.commonClass = commonClass;
this.threadID = threadID;
}
@Override
public void run() {
for (int i = 0; i < 20; i++) {
// Time interval before a name is called - The thread sleep between 1-10 seconds every time
Random random = new Random();
int randomNumber = random.nextInt(10) + 1;
int numberInThousand = randomNumber * 1000;
try {
Thread.sleep(numberInThousand);
} catch (InterruptedException e) {
e.printStackTrace();
}
// java monitor
commonClass.take((char) commonClass.nameEnteredIndex);
commonClass.callAName(this.threadID, commonClass.nameCalledIndex);
}
}
}
import java.util.ArrayList;
public class CommonClass {
// java monitor
int N = 10;
char[] buffer = new char[N];
int nextin, nextout, count;
public int nameEnteredIndex;
public int nameCalledIndex;
// names list with 20 names
public ArrayList<String> namesList() {
ArrayList<String> names = new ArrayList<>();
names.add("Hans");
names.add("Jens");
names.add("Rasmus");
names.add("Kasper");
names.add("Niels");
names.add("Torben");
names.add("Peter");
names.add("Michael");
names.add("Lars");
names.add("Anders");
names.add("Bo");
names.add("Klaus");
names.add("Ib");
names.add("Kevin");
names.add("Oscar");
names.add("Nicolaj");
names.add("Alexander");
names.add("Morten");
names.add("Carsten");
names.add("Jakob");
return names;
}
public synchronized void enterName(String name, int threadID) {
if (threadID == 0) {
System.out.println("Name-entered (entrance1): " + name);
} else if (threadID == 1) {
System.out.println("Name-entered (entrance2): " + name);
}
nameEnteredIndex++;
}
public synchronized void callAName(int threadID, int index) {
if (threadID == 0) {
System.out.println("Name called (caseworker1): " + namesList().get(index));
} else if (threadID == 1) {
System.out.println("Name called (caseworker2): " + namesList().get(index));
}
nameCalledIndex++;
}
// java monitor
public synchronized void append(char x) {
if (count == N) {
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
buffer[nextin] = x;
nextin = (nextin + 1) % N;
count++;
notifyAll();
}
// java monitor
public synchronized void take(char x) {
if (count == 0) {
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
x = buffer[nextout];
nextout = (nextout + 1) % N;
count--;
notifyAll();
}
}
public class MainApp {
public static void main(String[] args) {
// commonclass
CommonClass commonClass = new CommonClass();
// Thread - arrivals
ThreadClass_Arrivals threadClass_arrival1 = new ThreadClass_Arrivals(commonClass, 0);
ThreadClass_Arrivals threadClass_arrival2 = new ThreadClass_Arrivals(commonClass, 1);
threadClass_arrival1.start();
threadClass_arrival2.start();
// Thread - caseworkers
ThreadClass_Caseworkers threadClass_caseworker1 = new ThreadClass_Caseworkers(commonClass, 0);
ThreadClass_Caseworkers threadClass_caseworker2 = new ThreadClass_Caseworkers(commonClass, 1);
threadClass_caseworker1.start();
threadClass_caseworker2.start();
}
}
The problem is that some names are called before they are entered and I also get an ArrayOutOfBounceException even though there are 20 names in the list and there is a loop that retrieves the 20 names from the list in the 2 thread-subclasses.
Any help would be appreciated!