Unit - Iv 4.1 Multithreading Programming
Unit - Iv 4.1 Multithreading Programming
Multithreading Multitasking
Light weight process share the same address Heavy weight process that requires their own
space separate address space
Less Overhead High Overhead
Inter-Thread communication is in-expensive Inter-Process Communication is expensive
Context switching from one thread to the next Context switching from one process to another
is low cost is costly.
Multithreading enables to write efficient programs that make a maximum use of the CPU,
because idle time can be kept to a minimum.
Ex: Local File system resources are read and written at a much slower than they can be
processed by the CPU.
In a traditional single-threaded environment, program has to wait for each of these tasks
to finish before it can proceed to the next one, even though the CPU is sitting idle most of
the time.
4.3 THE JAVA THREAD LIFE CYCLE:
Java uses threads to enable the entire environment to be asynchronous.
This helps reduce inefficiency by preventing the waste of CPU cycles.
The single-threaded systems use an approach called an event loop with polling.
A single thread of control runs in an infinite loop, polling a single event queue to decide
what to do next.
Polling mechanisms returns saying that a network file is ready to be read, then the event
loop dispatches control to the appropriate event handler.
Until this event handler returns, nothing else can happen in the system. This waste CPU
time.
Results in one part of a program dominating the system and preventing any other events
from being processed.
In the single-threaded environment, when a thread blocks, because it is waiting for some
resource, the entire program stops running.
In java’s multithreading, the loop/polling mechanism is eliminated. One thread can pause
without stopping other parts of your program,
Ex: Idle time created when a thread reads data from a network or waits for user input can
be utilized elsewhere.
When a thread blocks, in a java program, only the single thread that is blocked pauses all
other threads continue to run.
Threads exist in several states: A thread can be running. It can be ready to run as soon as
it gets CPU time.
o A running thread can be suspended, which temporarily suspends its activity.
o A suspended thread can then be resumed, allowing it to pick up where it left off.
o A thread can be blocked when waiting for a resource.
o At anytime, a thread can be terminated, which halts its execution immediately.
Once terminated, a thread cannot be resumed.
4.3.2 Synchronization:
If any two threads to communicate and share a complicated data structure, such as a
linked list, There should be some way to ensure that they don’t conflict with each other.
(i.e.. when one thread is reading, we have to prevent another thread from waiting data to
it.)
Java implements a model of interprocess synchronization: the monitor.
Monitor is a control mechanism, it is viewed as a very small box that can hold only one
thread. Once a thread enters a monitor, all other threads must wait until that thread exits
the monitor.
In Java, each object has its own implicit monitor that is automatically entered when one
of the object’s synchronized methods is called. Once a thread is inside a synchronized
method, no other thread can call any other synchronized method on the same object.
class Synch
{
public static void main(String args[ ])
{
Callme target = new Callme();
Caller ob1 = new Caller(target, "Hello");
Caller ob2 = new Caller(target, "Synchronized");
Caller ob3 = new Caller(target, "World");
try
{
ob1.t.join( );
ob2.t.join( );
ob3.t.join( );
}
catch(InterruptedException e)
{
System.out.println("Interrupted");
}
}
}
Output: Hello [Synchronized [World]
]
]
By calling sleep( ), the call( ) method allows execution to switch to another thread.
This results in the mixed-up output of the three message strings.
In this program, nothing exists to stop all three threads from calling the same method, on
the same object, at the same time. This is known as a race condition, because the three
threads are racing each other to complete the method.
We must serialize access to call( ). That is restrict its access to only one thread at a time.
To do this, simply need to precede call( )’s definition with the keyword synchronized.
synchronized void call(String msg)
{
...
This prevents other threads from entering call( ) while another thread is using it.
class Q {
int n;
synchronized int get() {
System.out.println("Got: " + n);
return n;
}
synchronized void put(int n) {
this.n = n;
System.out.println("Put: " + n);
}
}
4.8 THREADGROUPS:
Thread groups is a way to manage groups of threads as a unit. This is useful when want to
suspend and resume a number of related threads.
Constructor
ThreadGroup(String name) – creates a thread group with given name
ThreadGroup(ThreadGroup parent, String name) – creates a thread group with the given parent
group and name.
public class ThreadGroupDemo implements Runnable
{
public void run()
{
System.out.println(Thread.currentThread().getName());
}
public static void main(String args[])
{
ThreadGroupDemo runnable = new ThreadGroupDemo();
ThreadGroup tg1 = new ThreadGroup(“Parent Thread Group”);
Thread t1 = new Thread(tg1, runnable, “one”);
t1.start();
Thread t2 = new Thread(tg1, runnable, “two”);
t2.start();
}
}
It enables to create classes , interfaces and methods in which the type of data upon which they
operate is specified as a parameter.
Using generics, it is possible to create single class that automatically works with different types
of data.
Java has the ability to create generalized classes, interfaces and methods by operating through
references of type Object. It can refer to any type of object.
class Gen<T> {
T ob; // declare an object of type T
// Pass the constructor a reference to
// an object of type T.
Gen(T o) {
ob = o;
}
// Return ob.
T getob() {
return ob;
}
// Show type of T.
void showType() {
System.out.println("Type of T is " +
ob.getClass().getName());
}
}
class GenDemo {
public static void main(String args[]) {
// Create a Gen reference for Integers.
Gen<Integer> iOb;
// Create a Gen<Integer> object and assign its
// reference to iOb. Notice the use of autoboxing
// to encapsulate the value 88 within an Integer object.
iOb = new Gen<Integer>(88);
// Show the type of data used by iOb.
iOb.showType();
// Get the value in iOb. Notice that
// no cast is needed.
int v = iOb.getob();
System.out.println("value: " + v);
System.out.println();
// Create a Gen object for Strings.
Gen<String> strOb = new Gen<String>("Generics Test");
// Show the type of data used by strOb.
strOb.showType();
// Get the value of strOb. Again, notice
// that no cast is needed.
String str = strOb.getob();
System.out.println("value: " + str);
}
}
The output produced by the program is shown here:
Type of T is java.lang.Integer
value: 88
Type of T is java.lang.String
value: Generics Test
T is the name of a type parameter. This name is used as a place holder for the actual type that
will be passed to Gen when an object is created.
Single generic method declaration that can be called with arguments of different types.
Based on the types of the arguments passed to the generic method, the compiler handles each
method call appropriately.
public class GenericMethodTest
{
public static <T> void printArray(T[] inputArray)
{
for(T element: inputArray)
{ System.out.printf(“%s”, element); }
}
public static void main(String args[])
{
Integer[] intArray = {1,2,3,4,5};
Double[] doubleArray = [1.1,2.2,3.3,4.4,5.5};
System.out.println(“Array contains”);
printArray(intArray);
printArray(doubleArray);
}
}
4.9.3 Bounded Types:
Restrict the kinds of types that are allowed to be passed to a type parameter.
Ex: a method that operates on numbers might want to accept instances of Number or its
subclasses.
To declare a bounded type parameter, list the type parameters’ name, followed by the extends
keyword, followed by its upper bound.