Using Java TreeMap

 
Today we will see about one of the important interface in Java called Map interface. Map interface and derived classes are in java.util.Map package and Map uses simple data structure that contains Key and Value. Always key must be unique Object and its uses Hashing to identify the correct Key and corresponding Value in the Sequential array (Used to call as bucket). 

Under Map interface lot of derived classes and lets see TreeMap in this tutorial.

TreeMap:
       TreeMap is an important class which implements the Map interface. As same as HashMap TreeMap also uses the Key/ Value to store the data in a sorted order. TreeMap can be created in 2 ways as natural sorted order or custom sorted order by using Comparator. Below we will see small examples for all these types.


Example: TreeMap using natural sort.


public class TreeMapTest {
 public static void main(String[] args) {
  TreeMap<String, String> map = new TreeMap<String, String>();
  map.put("4", "Delhi");
  map.put("3", "Mumbai");
  map.put("5", "Chennai");
  map.put("1", "Culcutta");
  map.put("2", "Bangalore");
  
  // Sorted TreeMap
  System.out.println("Sorted TreeMap values....");
  for (Map.Entry<String, String> entry : map.entrySet()) {
   System.out.println("KEY : "+entry.getKey() +" - VALUE : "+entry.getValue());
  }
  
  // Getting size TreeMap
  System.out.println("\nSize of TreeMap :: "+map.size());
  
  // Contains Key in TreeMap
  System.out.println("\nKey Contains (15) : "+map.containsKey("15"));
  System.out.println("Key Contains (4) : "+map.containsKey("4"));
    
  // Contains Value in TreeMap
  System.out.println("\nValue Contains (Delhi) : "+map.containsValue("Delhi"));
  System.out.println("Value Contains (Ney York) : "+map.containsValue("New York"));
    
  // Getting Reversing TreeMap
  NavigableMap<String, String> revMap = map.descendingMap();
  System.out.println("\nReverse TreeMap values....");
  for (Map.Entry<String, String> entry : revMap.entrySet()) {
   System.out.println("KEY : "+entry.getKey() +" - VALUE : "+entry.getValue());
  }
  
  // Get sub portion of map to subMap
  SortedMap<String, String> subMap = map.subMap("2","4");
  System.out.println("\nSub portion TreeMap values....");
  for (Map.Entry<String, String> entry : subMap.entrySet()) {
   System.out.println("KEY : "+entry.getKey() +" - VALUE : "+entry.getValue());
  }
  
  // Getting first Key and Entry in TreeMap
  System.out.println("\nFirst Key in TreeMap : "+map.firstKey());
  System.out.println("First Entry in TreeMap : "+map.firstEntry());
  
  // Getting last Key and Entry in TreeMap
  System.out.println("\nLast Key in TreeMap : "+map.lastKey());
  System.out.println("Last Entry in TreeMap : "+map.lastEntry());
  
  // Removing data from TreeMap
  map.remove("3");
  System.out.println("\nTreeMap size after removing 1 element : "+map.size());
  
  // Checking TreeMap is empty or not
  System.out.println("\nTreeMap empty or not : "+map.isEmpty());
  
  // Clearing complete TreeMap
  map.clear();
  System.out.println("\nTreeMap size after clearing all values : "+map.size());
  System.out.println("TreeMap empty or not : "+map.isEmpty());
  
 }
}



OUTPUT:


Sorted TreeMap values....
KEY : 1 - VALUE : Culcutta
KEY : 2 - VALUE : Bangalore
KEY : 3 - VALUE : Mumbai
KEY : 4 - VALUE : Delhi
KEY : 5 - VALUE : Chennai

Size of TreeMap :: 5

Key Contains (15) : false
Key Contains (4) : true

Value Contains (Delhi) : true
Value Contains (Ney York) : false

Reverse TreeMap values....
KEY : 5 - VALUE : Chennai
KEY : 4 - VALUE : Delhi
KEY : 3 - VALUE : Mumbai
KEY : 2 - VALUE : Bangalore
KEY : 1 - VALUE : Culcutta

Sub portion TreeMap values....
KEY : 2 - VALUE : Bangalore
KEY : 3 - VALUE : Mumbai

First Key in TreeMap : 1
First Entry in TreeMap : 1=Culcutta

Last Key in TreeMap : 5
Last Entry in TreeMap : 5=Chennai

TreeMap size after removing 1 element : 4

TreeMap empty or not : false

TreeMap size after clearing all values : 0
TreeMap empty or not : true



In above example we can see automatically TreeMap sorted and also other methods in TreeMap class.

Next we will see simple example using custom sorting using Comparator.

Example: TreeMap using custom sort - Comparator.




public class TreeMapUsingCustomComparator {
 
 public static void main(String a[]){
  TreeMap<Worker,String> map = new TreeMap<Worker, String>(new MyNameComp());
  map.put(new Worker("david",5000), "david");
  map.put(new Worker("joy",2000), "joy");
  map.put(new Worker("abel",7000), "abel");
  map.put(new Worker("ruby",9000), "ruby");
  
  for (Map.Entry<Worker, String> entry : map.entrySet()) {
   System.out.println("KEY : "+ entry.getKey() +" \t VALUE : "+entry.getValue());
  }
 }
}




public class Worker{
    
    private String name;
    private int salary;
    
    public Worker(String name, int salary){
        this.name = name;
        this.salary = salary;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public int getSalary() {
        return salary;
    }
    public void setSalary(int salary) {
        this.salary = salary;
    }
    public String toString(){
        return "("+this.name+":"+this.salary+")";
    }
}




public class MyNameComp implements Comparator<Worker>{
    public int compare(Worker obj1, Worker obj2) {
        return obj1.getName().compareTo(obj2.getName());
    }
}



OUTPUT: 


KEY : (abel:7000)   VALUE : abel
KEY : (david:5000)   VALUE : david
KEY : (joy:2000)   VALUE : joy
KEY : (ruby:9000)   VALUE : ruby





Using keySet(), entrySet() and values() methods in HashMap

Today we will see about using keySet(), value() and entrySet() methods in HashMap. Basically all these methods will be used to get the list of keys and values from HashMap. Lets see each one separately how its used in Java.
  • keySet() method is used to get only the list of keys in HashMap.
  • value() method is used to get only the list of values in HashMap.
  • entrySet() method is used to get both key and values from the HashMap.

Below is a simple example program which will explain about using all these 3 methods.

 


public class HashMapTest {
 
 public static void main(String[] args) {
 
    Map<String, String> hm = new HashMap<String, String>();
    hm.put("key1", "Bangalore");
    hm.put("key3", "India");
    hm.put("key2", "Mumbai");
    hm.put("key5", "New Delhi");
    hm.put("key4", "Chennai");
    
    new HashMapTest().getOnlyKeyList(hm);
    new HashMapTest().getOnlyValueList(hm);
    new HashMapTest().getBothKeyValue(hm);    
 }
 
 // Fetching only Keys by using keySet() method
 public void getOnlyKeyList(Map<String, String> hm){
  Iterator<String> itr = ((Set<String>) hm.keySet()).iterator();
  System.out.println("USING keyset() :::::::::::: ");
  while(itr.hasNext()){
   String key = itr.next();
   System.out.println("KEY : "+key);
  }
 }
 
 // Fetching only values by using value() method
 public void getOnlyValueList(Map<String, String> hm){
  Iterator<String> itr = hm.values().iterator();
  System.out.println("\n\nUSING value() :::::::::::: ");
  while(itr.hasNext()){
   String value = itr.next();
   System.out.println("VALUE : "+value);
  }
 }
 
 // Fetching both keys and values using entrySet() method
 public void getBothKeyValue(Map<String, String> hm){
  Iterator <Map.Entry<String,String>>entryset = hm.entrySet().iterator();
  System.out.println("\n\nUSING entryset() :::::::::::: ");
  while(entryset.hasNext()){
   Map.Entry <String,String>entry=entryset.next();
   String key = entry.getKey();
   String value = entry.getValue();
   System.out.println("KEY : "+key +" - VALUE : "+value);
  }
 }
}



OUTPUT:



USING keyset() :::::::::::: 
KEY : key1
KEY : key3
KEY : key5
KEY : key2
KEY : key4


USING value() :::::::::::: 
VALUE : Bangalore
VALUE : India
VALUE : New Delhi
VALUE : Mumbai
VALUE : Chennai


USING entryset() :::::::::::: 
KEY : key1 - VALUE : Bangalore
KEY : key3 - VALUE : India
KEY : key5 - VALUE : New Delhi
KEY : key2 - VALUE : Mumbai
KEY : key4 - VALUE : Chennai




Java Threads by Extending Thread class and Implementing Runnable Interface

 
Today we will discuss about the Threads in Java. Java Threads are nothing but multiple light weight execution under single process where all Threads will share same resources and runs independently. Most of all operatiing systems will support Threads and each and every Java programs are running atleast with single Thread. For example when Hello World programd starts, JVM creates the Main Thread and calls the program's main() method within same Thread. Also JVM creates other Thread internally to handle Garbage Collection activities. 

       Threads are used to run multiple task simultaneously and asynchronously under a single process. Threads are independent, concurrent paths of execution through a program, and each thread has its own stack own program counter and own local variables. Since each Threads will share same resources, its easy to share information's with each Threads. Just we need to take care on each Thread should not interfere with other threads in the same process.

       Using multi Threads are not easy in complex applications and programmers need to take on multiple Threads based on their business logic's. In Java we can implement Threads in 2 ways. First way by extending Thread class and other way by implementing Runnable interface. In this tutorial lets take a small example and we will discuss about both the ways in separately.


Example for extends Thread Class:



public class MyThreadClass extends Thread{
 
 public MyThreadClass() {}
 
 public MyThreadClass(String tName) {
  this.setName(tName); // Setting Thread name
 }
 
 @Override
 public void run() {
  System.out.println("Thread ::: "+this.getName() +" started");
  processMyThread();
  System.out.println("Thread ::: "+this.getName() +" Completed...");
 }
 
 private void processMyThread(){
  try {
   Thread.sleep(new Random().nextInt(1000));
  } catch (InterruptedException e) {
   e.printStackTrace();
  }
 }
}




public class ExtendThreadExample {
 public static void main(String[] args) {
  MyThreadClass obj1 = new MyThreadClass("Deposit");
  MyThreadClass obj2 = new MyThreadClass("Balance");
  MyThreadClass obj3 = new MyThreadClass("Withdraw");
  obj1.start();
  obj2.start();
  obj3.start();
 }
}




OUTPUT:



Thread ::: Balance started
Thread ::: Withdraw started
Thread ::: Deposit started
Thread ::: Withdraw Completed...
Thread ::: Deposit Completed...
Thread ::: Balance Completed...



       
        In above example we have used extending Thread class and we have Overrided run() method and we have given sample implementation. In 2nd class we have instantiated class for 3 times and we have pass Thread name for our identification.
       

       Once we complete 2nd type (implements Thread) we will discuss about which will be the best practice of using Threads in our application.


Example for implements Runnable interface:




public class MyThreadClass implements Runnable{
 
 public MyThreadClass() {}
 
 public void run() {
  System.out.println("Thread ::: "+Thread.currentThread().getName() +" started");
  processMyThread();
  System.out.println("Thread ::: "+Thread.currentThread().getName() +" Completed...");
 }
 
 private void processMyThread(){
  try {
   Thread.sleep(new Random().nextInt(1000));
  } catch (InterruptedException e) {
   e.printStackTrace();
  }
 }
}




public class ImplementsRunnableExample {
 public static void main(String[] args) {
  MyThreadClass obj = new MyThreadClass1();
  Thread t1 = new Thread(obj,"Deposit");
  Thread t2 = new Thread(obj,"Withdraw");
  Thread t3 = new Thread(obj,"Balance");
  t1.start();
  t2.start();
  t3.start();
 }
}



OUTPUT:



Thread ::: Deposit started
Thread ::: Withdraw started
Thread ::: Balance started
Thread ::: Deposit Completed...
Thread ::: Withdraw Completed...
Thread ::: Balance Completed...
 

Difference between Extending Thread and Implementing Runnable Interface:
 

  • By extending Thread class we are restricted that we can't extend other classes. Whereas while implementing Runnable interface we can extend other class also.
     
  • By extending we are inheriting complete Thread class into our class and we are Overriding only run() method. Whereas while implementing Runnable interface we are having our own implementation for run() method and just using Thread class by instantiating.
     
  • While extending Thread class we need to create multiple instance for our class, whereas in Runnable interface we can single class Object and can be passed to each Thread for its execution.

       Hence we can conclude that implementing Runnable interface will be best and hope you are cleat on the Java Threads. Still there are lot of important methods like wait(), notify(), notifyAll(), join(), yield(), sleep()  which we can discuss in our next tutorial.



 

Java 7 - Underscores in Numeric Literals

 
In this tutorial we will discuss about Underscore in Numberic feature added in Java 7. This is a nice and small feature which has added in Java 7 gives good readability for our codes. Its nothing but we can use underscores ( _ ) in-between numberic values in our code. Underscore can be added anywhere in the value part with few constraints listed below,

ALLOWED:
In-between 2 numbers or hexadecimal values or binary values are allowed. Below are the few valied literals by using underscore which are given in Oracle docs.

long creditCardNumber = 1234_5678_9012_3456L;
long socialSecurityNumber = 999_99_9999L;
float pi = 3.14_15F;
long hexBytes = 0xFF_EC_DE_5E;
long hexWords = 0xCAFE_BABE;
long maxLong = 0x7fff_ffff_ffff_ffffL;
byte nybbles = 0b0010_0101;
long bytes = 0b11010010_01101001_10010100_10010010;

NOT ALLOWED:

Can't place underscore at beginning or end of the numberic value.
Adjacent to a decimal point in a floating point value literal is not allowed
Prior to an F or L suffix are not allowed
Positions where a string of digits is expected are not allowed
 

float pi1 = 3_.1415F; // Invalid; cannot put underscores adjacent to a decimal point
float pi2 = 3._1415F; // Invalid; cannot put underscores adjacent to a decimal point
long socialSecurityNumber1 = 999_99_9999_L;         // Invalid; cannot put underscores prior to an L suffix

int x1 = _52;            // This is an identifier, not a numeric literal
int x2 = 5_2;            // OK (decimal literal)
int x3 = 52_;            // Invalid; cannot put underscores at the end of a literal
int x4 = 5_______2;  // OK (decimal literal)

int x5 = 0_x52;        // Invalid; cannot put underscores in the 0x radix prefix
int x6 = 0x_52;        // Invalid; cannot put underscores at the beginning of a number
int x7 = 0x5_2;        // OK (hexadecimal literal)
int x8 = 0x52_;        // Invalid; cannot put underscores at the end of a number

int x9 = 0_52;         // OK (octal literal)
int x10 = 05_2;       // OK (octal literal)
int x11 = 052_;       // Invalid; cannot put underscores at the end of a number
 

Lets see one small example by using underscore in numeric literals.
 



public class LiteralsExample {
   public static void main(String[] arg){
       
       float x1 = 52.4_5F;              
       float x2 = 5_2.12F;            
       
       int x3 = 52_3;              
       int x4 = 5_______2;        
       
       System.out.println("FLOAT VALUE :"+(x1+x2));
       System.out.println("INT VALUE   :"+(x3+x4));    
   }
}



OUTPUT:


FLOAT VALUE :104.57
INT VALUE   :575





Creating own ThreadPool using ThreadGruop

 
Welcome to this tutorial. In this tutorial we will discuss about creating our own ThreadPool by limiting no. of threads and pool size. We have 2 class called ThreadPoolTester and MyThreadPool where in ThreadPoolTester we are implementing the run() method and returning the Runabble instance.  Each instance are managed by other class called MyThreadPool which extends the ThreadGroup class. Below are those 2 classes sample code and sample output. 




public class ThreadPoolTester {

 public static void main(String[] args) {
  // Assign your no. of thread to create 
  int noOfProcess = 5; 
  // Assign your own thread pool size
  int poolMaxSize = 2;

  // Creating Threadpool with the thread size given above
  MyThreadPool threadPool = new MyThreadPool(poolMaxSize);
  // Creating threadpool Object
  ThreadPoolTester obj = new ThreadPoolTester();
  long time1 = getTime();

  for (int i = 0; i < noOfProcess; i++) {
   threadPool.process(obj.startProcess(i));
   
   /**
    * Just for showing threadpool not empty we have 
    * place this while loop and making thread to sleep 
    * In realtime while loop should not there, since it
    * will create performance issue. 
    */
   while (threadPool.getTaskListSize() >= poolMaxSize) {
    try {
     System.out.println("Threadpool NOT Empty           - " + threadPool.getTaskListSize());
     Thread.sleep(1000);
     System.out.println("Threadpool size after sleeping - " + threadPool.getTaskListSize());
    } catch (Exception e) {
     e.printStackTrace();
    }
   }
  }
  
  // Finally waiting for all thread to complete its process
  threadPool.join();
  long time2 = getTime();
  System.out.println("Time Taken ::: " + (time2 - time1) +" millisecond(s)");
 }

 private Runnable startProcess(final int taskID) {
  return new Runnable() {
   public void run() {
    System.out.println("Task " + taskID + ": start");
    
    // Putting each task to wait for random milli seconds
    try {
     Thread.sleep(new Random().nextInt(2000));
    } catch (InterruptedException ex) {
    }

    System.out.println("Task " + taskID + ": end");
   }
  };
 }

 public static long getTime() {
  Calendar currentDate = Calendar.getInstance();
  long time = currentDate.getTimeInMillis();
  return time;
 }
}




/**
 * Main ThreadPool class where we are extending ThreadGroup 
 * to implement our own pooling
 */
public class MyThreadPool extends ThreadGroup {
 private boolean active = false;
 private LinkedList<Runnable> qList = null;
 private int tId = 0;
 private static int tPoolID = 0;

 public MyThreadPool(int numThreads) {
  super("Pool - " + (tPoolID++));
  setDaemon(true);
  active = true;
  qList = new LinkedList<Runnable>();
  for (int i = 0; i < numThreads; i++) {
   new PooledThread().start();
   try {
    Thread.sleep(100);
   } catch (InterruptedException e) {
    e.printStackTrace();
   }
  }
 }

 public synchronized void process(Runnable task) {
  if (!active) {
   throw new IllegalStateException();
  }
  if (task != null) {
   qList.add(task);
   notify();
  }

 }

 protected synchronized Runnable getTask() throws InterruptedException {
  while (qList.size() == 0) {
   if (!active) {
    return null;
   }
   wait();
  }
  return (Runnable) qList.removeFirst();
 }

 protected int getTaskListSize() {
  return qList.size();
 }

 public synchronized void close() {
  if (active) {
   active = false;
   qList.clear();
   interrupt();
  }
 }

 public void join() {
  synchronized (this) {
   active = false;
   notifyAll();
  }
  Thread[] threads = new Thread[activeCount()];
  int count = enumerate(threads);
  for (int i = 0; i < count; i++) {
   try {
    threads[i].join();
   } catch (InterruptedException ex) {
   }
  }
 }

 private class PooledThread extends Thread {

  public PooledThread() {
   super(MyThreadPool.this, "Task -" + (tId++));
  }

  public void run() {
   while (!isInterrupted()) {
    Runnable process = null;
    try {
     process = getTask();
    } catch (InterruptedException ex) {}
    if (process == null) {
     return;
    }
    try {
     process.run();
    } catch (Throwable t) {
     uncaughtException(this, t);
    }
   }
  }
 }
}



OUTPUT:


Task 0: start
Threadpool NOT Empty           - 2
Task 1: start
Task 1: end
Task 2: start
Task 0: end
Threadpool size after sleeping - 0
Threadpool NOT Empty           - 2
Task 3: start
Task 3: end
Task 4: start
Threadpool size after sleeping - 0
Task 2: end
Task 4: end
Time Taken ::: 3285 millisecond(s)