June 03, 2021
These blogs will help you learn Java Programming & Concepts in a simple and effective way. If you have no prior knowledge in Java, you won’t face any difficulty. If you are experienced java developer, this blog will help you brush up the concepts.
Any class whose Object’s state cannot be changed once it is instantiated are called Immutable.
This is how we can make a class immutable:
Question: Why is String immutable in Java?
String a = “abcd”;
String b = “abcd”;
System.out.println(a == b); // True
System.out.println(a.equals(b)); // True
String c = new String(“abcd”);
String d = new String(“abcd”);
System.out.println(c == d); // False
System.out.println(c.equals(d)); // True
== Checks memory locations where as equals() checks value, using constructor will create an extra unnecessary object
. Therefore, double quotes should be used if you just need to create a String.
So S1.intern() == S2.intern(), only if S1.equals(S2) is true.
CompareTo(Object obj)
Compare(Object obj1, Object obj2)
class HDTV implements Comparable<HDTV> {
private int size;
private String brand;
public HDTV(int size, String brand) {
this.size = size;
this.brand = brand;
}
// .. getters & setters
@Override
public int compareTo(HDTV tv) {
if (this.getSize() > tv.getSize())
return 1;
else if (this.getSize() < tv.getSize())
return -1;
else
return 0;
}}
public class Main {
public static void main(String[] args) {
HDTV tv1 = new HDTV(55, “Samsung”);
HDTV tv2 = new HDTV(60, “Sony”);
if (tv1.compareTo(tv2) > 0) {
System.out.println(tv1.getBrand() + “ is better.”);
} else {
System.out.println(tv2.getBrand() + “ is better.”);
}
}}
class SizeComparator implements Comparator<HDTV> {
@Override
public int compare(HDTV tv1, HDTV tv2) {
int tv1Size = tv1.getSize();
int tv2Size = tv2.getSize();
if (tv1Size > tv2Size) {
return 1;
} else if (tv1Size < tv2Size) {
return -1;
} else {
return 0;
}
}}
public class Main {
public static void main(String[] args) {
HDTV tv1 = new HDTV(55, “Samsung”);
HDTV tv2 = new HDTV(60, “Sony”);
HDTV tv3 = new HDTV(42, “Panasonic”);
ArrayList<HDTV> al = new ArrayList<HDTV>();
al.add(tv1);
al.add(tv2);
al.add(tv3);
Collections.sort(al, new SizeComparator());
for (HDTV a : al) {
System.out.println(a.getBrand());
}
}}
Collection is any data structure where objects are stored and iterated over. Data Structure in itself is a huge topic and I will try to cover it in a separate series. Here, we will try to cover some basic data structures in java collection libraries.
List mylist = Collections.synchronizedList(mylist);
// Single lock for the entire list
ListIterator extends Iterator and allow bidirectional traversing.
Collection classes are fail first, i.e. if one thread changes the value while the other on is traversing it will give ConcurentModificationException. Even if we use SynchronizedList/SynchronizedMap still it will throw this exception coz these are conditionally threadsafe, which means individual operations are threadsafe but not the whole operation. So either Synchronize block can be used or ConcurentHashMap or CopyOnWriteArrayList. ConcurentHaspMap, CopyOnWriteArrayList and CopyOnWriteArraySet are thread safe or synchronized.
A hash value is calculated using key’s hash code by calling its hashCode() method. This hash value is used to calculate index in array for storing Entry object. JDK designers well assumed that there might be some poorly written hashCode() functions that can return very high or low hash code value. So there is another hash() function, and passed the object’s hash code to this hash() function to bring hash value in range of array index size.
List testList = Collections. EMPTY_LIST;
Arrays.asList(T… a) returns the java.util.Arrays.ArrayList and not java.util.ArrayList. Its just a view of original Array.
Collection<String> listOne = new ArrayList(Arrays.asList(“a”,”b”, “c”,”g”));
Collection<String> listTwo = new ArrayList(Arrays.asList(“a”,”b”,”d”, “e”));
List<String> sourceList = new ArrayList<String>(listOne);
List<String> destinationList = new ArrayList<String>(listTwo);
sourceList.removeAll( listTwo ); // Result: [c, g]
destinationList.removeAll( listOne ); // Result: [d, e]
Question: How can we reverse the order in the TreeMap?
Using Collections.reverseOrder()
Map tree = new TreeMap(Collections.reverseOrder());
Question: Can we add heterogeneous elements into TreeMap?
No, Sorted collections don’t allow addition of heterogeneous elements as they are not comparable. It’s okay if they class implements comparable.
Question: Difference between int[] x; and int x[]
No Difference. Both are the acceptable ways to declare an array.
ArrayList < LinkedList < HashTable < HashMap < HashSet
Guava is Google’s Core Libraries for Java with some more added classes and interfaces to Collection.
Now that we are clear with some basic concepts, lets briefly look into some history and evolution of various versions of java.
Lambda Expressions: It’s a method without a declaration, i.e., access modifier, return value declaration, and name. It saves you the effort of declaring and writing a separate method to the containing class. They enable you to treat functionality as a method argument, or code as data.
MathOperation addition = (int a, int b) -> a + b;
addition(a,b);
Date\Time APIs: The current time is represented by the Clock class. The class is abstract, so you cannot create instances of it. The systemUTC() static method will return the current time.
import javax.time.Clock;
Clock clock = Clock.systemUTC();
Clock clock = Clock.systemDefaultZone();
ZoneId zone = ZoneId.of(“Europe/Berlin”);
// ZoneId zone = ZoneId.systemDefault(); you can also use this
Clock clock = Clock.system(zone);
import javax.time.LocalDate;
LocalDate date = LocalDate.now();
Stream: A stream is a one-time-use Object. Once it has been traversed, it cannot be traversed again. Streams have the ability to filter, map, and reduce while being traversed. Using a sequential stream:
List <Person> people = list.getStream.collect(Collectors.toList());
Using a parallel stream:
List <Person> people = list.getStream.parallel().collect(Collectors.toList());