Practice Session 9 Exchanger CyclicBarrier Exceptions
java.util.concurrent.Exchanger A combination of a barrier with data passing between threads. Allows a pair of threads to wait for each other at a rendezvous point. Allows exchange of data between the two threads at that point. Notes: – Two threads must be paired together for this to work. – The two threads must exchange data at the rendezvous point. How is exchanging data done? – Using exchange() method.
java.util.concurrent.Exchanger How is exchanging data done? – Thread A reaches rendezvous point, and executes the exchange() method: If thread B is already waiting, the data is passed. If thread B is not waiting, thread A waits for thread B: – For unlimited time: exchange(V x) – With a specified timeout: exchange(V x, long timeout, TimeUnit unit) » x: the object to be exchanged. » timeout: the number of TimeUnit to wait. » unit: java.util.concurrent.TimeUnit MICROSECONDS MILLISECONDS NANOSECONDS SECONDS API: Code Example: Exchanger
java.util.concurrent.CyclicBarrier A synchronization aid that allows a set of threads to all wait for each other to reach a common barrier point. CyclicBarriers are useful in programs involving a fixed sized group of threads that must occasionally wait for each other. The barrier is called cyclic because it can be re-used after the waiting threads are released. API:
Creating a CyclicBarrier – CyclicBarrier barrier = new CyclicBarrier(2); //specify how many threads are to wait at it, before releasing them. – CyclicBarrier barrier = new CyclicBarrier(2, barrierAction); //barrierAction is a Runnable that is executed once the last thread arrives.
Waiting at a CyclicBarrier: – barrier.await(); – barrier.await(10,TimeUnit.Seconds); The waiting thread waits at the barrier until either: – The last thread arrives (calls await()) – The thread is interrupted by another thread – Another waiting thread is interrupted – Another waiting thread times out while waiting at the barrier. – The CyclicBarrier reset() methods is called by some external thread.
Example Sum all values in a matrix IntHolder – a synchronized class to hold the sum of the matrix elements; updated by 2 threads summing matrix rows. MeetingPointAction – creates a meeting point, and 2 threads to work on 2 consecutive rows. The barrier action is a new MeetingPointAction
Advanced Synchronization Methods Semaphore: a lock with N permits; N threads may acquire a key at the same time. A thread can acquire more than one Permit using: acquire( ). CountDownLatch: Allows one or more threads to wait until other threads complete; Used for initialization/finalization purposes. Exchanger: Allows a pair of threads to wait for each other at a rendezvous point, and exchange data. CyclicBarrier: same as Exchanger but for any number of fixed threads; can be reused.
Exceptions
Java uses exceptions to handle errors and other exceptional events. Examples: Reading a file that does not exist or is inaccessible. Dividing a number by zero. Network is down, URL does not exist. Accessing an array element at a certain index that is not within the bounds of the array.
Code Example public class ExceptionExample { public static void main(String[] args) { int[] a = {2, 4, 6, 8}; for(int j = 0; j <= a.length ; j++) System.out.println(a[j]); } /* output: Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 4 at spl.examples.exceptions.ExceptionExample.main(ExceptionExample.java:7) */
What Is an Exception? An exception is an event that occurs during the execution of a program disrupting the normal flow of instructions. When an error occurs within a method: – the method creates an object and hands it off to the runtime system. – The object, called an exception object, contains information about the error, including its type and the state of the program when the error occurred. Creating an exception object and handing it to the runtime system is called throwing an exception.
After a method throws an exception, the runtime system attempts to find something to handle it. Call Stack: – The ordered list of methods that had been called to get to the method where the error occurred. – This is the set of possible "somethings" to handle the exception.
The runtime system searches the call stack for a method that contains a block of code that can handle the exception, exception handler. The search begins with the method in which the error occurred and proceeds through the call stack in the reverse order in which the methods were called. If no handler is found, the exception is thrown to the JVM, which terminates the program, and prints the exception together with its call stack to the console.
Exception Types There are 2 different types of exceptions: Unchecked Exceptions: – Errors: External to the application The application usually cannot anticipate or recover from them. They are indicated by Error and its subclasses. Example: OutOfMemoryError - the application ran out of memoryOutOfMemoryError
– Runtime Exceptions: Internal to the application The application usually cannot anticipate or recover from. Usually indicate programming bugs, such as logic errors or improper use of an API. Runtime exceptions are those indicated by RuntimeException and its subclasses. Examples: – NullPointerException - the application is trying to access a null pointer (an uninitialized object). NullPointerException – ArrayIndexOutOfBoundsException - the application is trying to access an array outside of its boundaries. ArrayIndexOutOfBoundsException
Checked Exceptions: – Exceptional conditions that a well-written application should anticipate and recover from. – Inherited from the core Java class Exception.Exception – Checked exceptions must be handled in your code (catch it), or passed to the calling code for handling (declare that your method might throw it using the throws keyword at the method signature). – Example: FileNotFoundException - the application is trying to access a file that does not exist.FileNotFoundException
Exception Hierarchy
Throwing an Exception public class Clock { private int fHours, fMinutes, fSeconds; // constructors and methods //There is no need to catch IllegalArgumentException or to declare that the function throws it //since it's a RuntimeException (unchecked exception). public void setTime(int hours, int minutes, int seconds){ if (hours 12 || minutes 59 || seconds 59) throw new(IllegalArgumentException(“Invalid time”); //this code does not run if an exception occurs. fHours = hours; fMinutes = minutes; fSeconds = seconds; }
Creating New Exceptions Create a new exception by extending Exception, or one of its subclasses.Exception //a class that uses our new exception public class Stack { int elements[]; int top; //next empty location in the elements array //... constructor, push(), isEmpty() //There is no need to declare StackUnderflowException a s thrown in the method signature //since it's a RuntimeException (unchecked exception) public int pop() { if (isEmpty()) throw new StackUnderflowException(); return elements[--top]; } //StackUnderflowException inherits all of its parent's methods and does not add any of its own //You can also add methods to StackUnderflowExcep tion or override existing methods to change //printing format, for example public class StackUnderflowException extends Runti meException {}
Catching Exceptions A method catches an exception using a combination of the try and catch keywords. A try/catch block is placed around the code that might generate an exception. Each catch block is an exception handler and handles the type of exception indicated by its argument, which must inherits from the Throwable class.Throwable
import java.io.*; public class FirstLine { public static void main(String[] args){ String name = args[0]; try{ BufferedReader file = new BufferedReader(new FileReader(name)); String line = file.readLine(); System.out.println(line); //handle FileNotFoundException }catch (FileNotFoundException e) { System.out.println("File not found: "+ name); //handle IOException }catch (IOException e) { System.out.println("Problem: " + e); }
Handling Exceptions When handling exceptions you should restore stable state and do one of the following: – Change conditions and retry. – Clean up and fail (re-throw exception) If an exception extends another exception and you would like to handle each separately, then the catch block that handles the sub exception should be before the catch block that handles the base exception.
Exceptions don't have to be handled in the method in which they occurred. You can let a method further up the call stack handle the exception. This is done by adding a throws clause to the method declaration. public BufferedReader openFileForReading(String filename) throws IOException{ return new BufferedReader(new FileReader(filename)); }
The Finally Block Comes right after all catch blocks in a try-catch clause. The code found in the finally block is always executed before exiting the try/catch block, even if an exception occurred, or a return/continue/break statement were encountered. It is usually used for cleanup code, since it allows the programmer to avoid having cleanup code accidentally bypassed by a return, continue, or break. For more information regarding exceptions see: Oracle Exceptions Tutorial.Oracle Exceptions Tutorial
import java.io.*; public class FirstLine { public static void main(String[] args){ String name = args[0]; try{ BufferedReader file = new BufferedReader(new FileR eader(name)); String line = file.readLine(); System.out.println(line); //handle FileNotFoundException }catch (FileNotFoundException e) { System.out.println("File not found: "+ name); //handle IOException }catch (IOException e) { System.out.println("Problem: " + e); }finally{ if (file != null) { System.out.println("Closing the file:" + na me); file.close(); } else { System.out.println("Unable to open file:" + name); }