JAVA Q_A?
- megha dureja
- Jun 6, 2020
- 6 min read
Updated: Mar 24, 2021

Q1) Define abstraction and what is the difference between abstract class and interface?
Abstraction refers to showing only the necessary details to the intended user. Abstraction is implemented using interface and abstract class.
Interface and Abstract class both are looks similar from declaration point of view.
- But an Interface contains only the definition / signature of functionality, and if we have some common functionality as well as common signatures, then we need to use an abstract class.
1. Abstract class (0 to 100%)
2. Interface (100%)
- Abstract class does not support multiple inheritance. Interface supports multiple inheritance.
- Abstract class contains constructors but Interface can't.
- Abstract class establishes "is a" relation with concrete classes. Interface provides "has a" capability for classes.
Q2) Can abstract class have constructor method?
Yes, it can have a constructor and it is defined and behaves just like any other class's constructor. Except that abstract classes can't be directly instantiated, only extended, so the use is therefore always from a subclass's constructor.
Q3) How will we invoke abstract class constructor?
You would define a constructor in an abstract class if you are in one of these situations:
you want to perform some initialization (to fields of the abstract class) before the instantiation of a subclass actually takes place
you have defined final fields in the abstract class but you did not initialize them in the declaration itself; in this case, you MUST have a constructor to initialize these fields
abstract class Parent {
int x;
public Parent(int x) {
this.x = x;
}
public int method(int val) {
return x * val;
}
}
class Child extends Product {
public Child(int y) {
super(y);
}
}
In any case, don't forget that if you don't define a constructor, then the compiler will automatically generate one for you (this one is public, has no argument, and does nothing).
Q4) Why we need default methods in Java 8 Interface?
The default methods are introduced to provide backward compatibility. Let’s imagine that we have an interface that has been implemented by a lot of classes. After some time, you want to introduce a new method in this interface. You will break a lot of classes and the effort to refactor (implementing the new method in all implementations of this interface) is huge since an interface is a contract that requires all implementations to follow a pattern. To solve this headache like a painkiller now we have a default method!
Q5) Does java.util.List.isEmpty() check if the list itself is null?
No
Q6) How to get first item from a java.util.Set?
Optional<Product> product = products
.stream()
.findFirst();
Q7) How to make a new list with a property of an object which is in another list?
List<Long> ids = products
.stream()
.map(Product::getId)
.collect(Collectors.toList());
Q8) How to make a new list of an object from another list based on some condition?
List<Product> ids = products
.stream()
.filter(p->p.getPrice() > 1000)
.collect(Collectors.toList());
Q9) How to fetch the latest record from List based on date?
Optional<Product> product = products
.stream()
.max(Comparator.comparing(Product::getCreatedDate));
Q10) Can we break out of a forEach loop when going through an Array?
No, There is no way to stop or break a forEach() loop other than by throwing an exception. If you need such behaviour, the . forEach() method is the wrong tool, use a plain loop instead.
Q11) What is multiple inheritance in Java?
Though classes can inherit multiple interfaces but multiple inheritance of implementations/classes is not allowed.
An interface can extend one or more other interfaces. You can also implement more than one interface in your classes.
public interface A {
void a();
}
public interface B {
void b();
}
public interface AB extends A, B {
}
public class ABImpl implements A, B {
public void a() {}
public void b() {}
}
Inheriting multiple interfaces isn't problematic, since you're simply defining new method signatures to be implemented.
Q12) What is a diamond problem?
The diamond problem occurs with the multiple inheritance of implementations/classes where two methods have the same name. This is because there is no obvious choice to the question "What implementation of f() do I use?" with multiple implementations.
The issue does not occur with multiple interfaces of the same method name because it does not need to make this selection.
A
/ \
B C
\ /
D
Above problem describe an ambiguous situation for class D. If class A has a method and both/either of B and/or C override the method then which version of method does D override?
Q13) How Java8 still avoids the diamond problem even though interfaces can have default implementations of methods?
There are three rules to follow:
A class always wins. Class's own method implementation takes priority over default methods in Interfaces.
If class doesn't have any: the most specific interface wins
public interface A {
default void doStuff();
}
public interface B extends A {
default void doStuff();
}
public class C implements A, B {
//will use doStuff() from B
}
3. If above is not the case, inheriting class has to explicitly state which method implementation it's using (otherwise it won't compile)
public interface A {
default void doStuff();
}
public interface B {
default void doStuff();
}
public class C implements A, B {
doStuff(){
B.super.doStuff();
}
}
Q14) How do I compare strings in Java?
== compares Object references .equals() compares String values
Q15) What is functional interfaces in Java 8 and why do we need them?
An interface with only one abstract method is called Functional Interface. It may have more than one method, but all of the others must have a default implementation. The reason it's called a "functional interface" is because it effectively acts as a function.
public interface Foo { public void doSomething(); }
@FunctionalInterface
public interface Foo { public void doSomething(); }
Both are functional interface and can be used in lambda expression.
It is not mandatory to use @FunctionalInterface, but it’s a best practice to use to avoid addition of extra methods accidentally. If the interface is annotated with @FunctionalInterface annotation and we try to have more than one abstract method, it throws a compiler error.
Applications of Functional Interface:
Method references
Lambda Expression
Constructor references
Q16) What is lambda expression in Java8?
Lambda expression facilitate functional programming, accepts input parameters and produces output
eg:- (arg1,agr2) -> { body }
Lambda expression is used to instantiate functional interface
Lambda expression can be passed as a parameter to method
Lambda expression is generally use with Stream Intermediate/Terminal Operations (Methods) like filter, map, flatMap, reduce etc
Q17) What is Stream in Java8?
A stream represents a sequence of elements and supports different kind of operations to perform computations upon those elements:
We can use Stream.of() to create a stream from a bunch of object references.
Stream operations are either intermediate or terminal.
Intermediate operations return a stream so we can chain multiple intermediate operations without using semicolons.
Terminal operations are either void or return a non-stream result.
In the below example filter, map and sorted are intermediate operations whereas forEach is a terminal operation.
List<String> myList = Arrays.asList("a1","a2","b1","c2","c1");
myList
.stream()
.filter(s -> s.startsWith("c"))
.map(String::toUpperCase)
.sorted()
.forEach(System.out::println);
Most stream operations accept some kind of lambda expression parameter, a functional interface specifying the exact behavior of the operation.
An important characteristic of intermediate operations is laziness. Intermediate operations will only be executed when a terminal operation is present.
Q18) What is an immutable class and how to make an object immutable? And what is the advantage of immutability?
An immutable class is a class whose instances cannot be modified.
or An immutable object is one that will not change state after it is instantiated.
Following are the requirements to make a Java class immutable:
Class must be declared as final (So that child classes can’t be created)
Members in the class must be declared as final (So that we can’t change the value of it after object creation)
Only write Getter methods but No Setters methods
Clone deeply if it contain non primitive or mutable classes.
The advantage of immutability comes with concurrency. It is difficult to maintain correctness in mutable objects, as multiple threads could be trying to change the state of the same object, leading to some threads seeing a different state of the same object, depending on the timing of the reads and writes to the said object.
By having an immutable object, one can ensure that all threads that are looking at the object will be seeing the same state, as the state of an immutable object will not change.
So In Short:-
Caching purpose
Concurrent environment (Immutable objects are inherently thread-safe; they require no synchronization)
Hard for inheritance
Q19) What is shallow and deep copy?
When we want to copy an object in Java, there're two possibilities that we need to consider — a shallow copy and a deep copy.
class User {
private String firstName;
private String lastName;
private Address address; //problem
// standard constructors, getters and setters
}
class Address {
private String street;
private String city;
private String country;
// standard constructors, getters and setters
}
shallow copy - we only copy values of fields from one object to another
Address address = new Address("Downing St 10", "London", "England");
User pm = new User("Prime", "Minister", address);
User shallowCopy = new User(
pm.getFirstName(), pm.getLastName(), pm.getAddress());
In this case pm != shallowCopy, which means that they're different objects, but the problem is that when we change any of the original address' properties, this will also affect the shallowCopy‘s address.
We wouldn't bother about it if Address was immutable, but it's not.
deep copy - is an alternative that solves this problem. Its advantage is that at least each mutable object in the object graph is recursively copied.
Copy Constructor
public User(User that) {
this(that.getFirstName(), that.getLastName(), new Address(that.getAddress()));
}
public Address(Address that) {
this(that.getStreet(), that.getCity(), that.getCountry());
}
Address address = new Address("Downing St 10", "London", "England");
User pm = new User("Prime", "Minister", address);
User deepCopy = new User(pm);
Cloneable Interface
Inherit marker interface Cloneable and implement clone() method in above classes
Comentários