What is the difference between JDK, JRE, and JVM?
This is a fundamental concept in Java.
rt.jar
) and other supporting files. You would provide the JRE to a user who only needs to run your Java application, not develop it.javac
), debugger (jdb
), and archiver (jar
). You need the JDK to write and compile Java code.In short, the hierarchy is: JDK > JRE > JVM.
What are the main principles of Object-Oriented Programming (OOP)?
The four main principles of OOP are:
private
access modifiers).extends
keyword for class inheritance.Why is Java considered 'Platform Independent'?
Java's platform independence is one of its most famous features, summed up by the slogan 'Write Once, Run Anywhere' (WORA).
This is achieved through the use of Java bytecode and the Java Virtual Machine (JVM).
.java
file), the Java compiler (javac
) compiles it not into machine code for a specific processor, but into an intermediate format called bytecode (a .class
file).Since there are specific JVMs available for almost all platforms, the same bytecode can be run on any of them without modification, making Java platform-independent.
What is the difference between `String`, `StringBuilder`, and `StringBuffer`?
This is a classic Java interview question that tests understanding of immutability and performance.
Feature | String | StringBuilder | StringBuffer |
---|---|---|---|
Mutability | Immutable. Once a String object is created, it cannot be changed. Any modification creates a new String object. | Mutable. It can be modified after it is created without creating a new object. | Mutable. Same as StringBuilder. |
Thread Safety | Thread-safe, due to its immutability. | Not thread-safe. It does not provide any synchronization. | Thread-safe. Its methods are synchronized . |
Performance | Slower for frequent modifications because it creates a new object for every change, leading to garbage collection overhead. | Faster than StringBuffer because it is not synchronized. It is the preferred choice for single-threaded applications. | Slower than StringBuilder due to the overhead of synchronization. |
When to Use | For fixed string values that won't change, or in multi-threaded environments where sharing is required. | In single-threaded environments where you need to perform many string modifications (e.g., building a long string in a loop). | In multi-threaded environments where a mutable string needs to be safely shared among threads. |
Why are Strings immutable in Java?
String immutability is a deliberate design choice in Java for several important reasons:
What is the difference between method overloading and method overriding?
Both are forms of polymorphism in Java.
Method Overloading (Compile-time Polymorphism / Static Binding):
class Calculator {
int add(int a, int b) {
return a + b;
}
double add(double a, double b) {
return a + b;
}
}
Method Overriding (Runtime Polymorphism / Dynamic Binding):
@Override
annotation is used to indicate this.class Animal {
void makeSound() {
System.out.println("Generic animal sound");
}
}
class Dog extends Animal {
@Override
void makeSound() {
System.out.println("Woof woof");
}
}
What is the difference between an `abstract class` and an `interface`?
Both are used to achieve abstraction, but they have key differences.
Feature | Abstract Class | Interface |
---|---|---|
Methods | Can have both abstract (no body) and concrete (with body) methods. | Before Java 8, could only have abstract methods. Since Java 8, can also have default and static methods with implementation. |
Variables | Can have final, non-final, static, and non-static variables. | Variables are implicitly public static final (constants). |
Inheritance | A class can extend only one abstract class (Java does not support multiple inheritance of classes). | A class can implement multiple interfaces. |
Constructor | Can have a constructor, which is called when an instance of a subclass is created. | Cannot have a constructor. |
Access Modifiers | Class members can have public , protected , private , or default access. | Methods are implicitly public . |
When to Use | Use when you want to provide a base class with some common implemented functionality and some methods that must be implemented by subclasses. Think 'is-a' relationship with shared code. | Use when you want to define a contract of behavior that implementing classes must adhere to, without specifying any implementation. Think 'has-a' capability. |
Explain the `final` keyword in Java.
The final
keyword is a non-access modifier used to restrict a class, method, or variable.
final
, its value cannot be changed once it has been assigned. It essentially becomes a constant. If a final variable is not initialized at the time of declaration, it is called a 'blank final variable' and must be initialized in the constructor.final
, it cannot be overridden by any subclass. This is used to prevent unexpected behavior from a subclass changing a core method's logic.final
, it cannot be extended (inherited) by any other class. For example, the String
class in Java is a final class.Explain the `static` keyword in Java.
The static
keyword is used for memory management mainly. It indicates that the particular member belongs to the class itself, rather than to an instance of the class.
ClassName.methodName()
). It can only access static data members and can only call other static methods directly. It cannot use the this
or super
keywords. The main
method is a common example.static
keyword. It is executed only once, when the class is first loaded into memory by the JVM. It is used to initialize static variables.What is the difference between `==` and the `.equals()` method?
==
operator is used for reference comparison (for non-primitive types). It checks if two object references point to the exact same object in memory. For primitive types (like int
, char
), it checks for value equality..equals()
method is used for content comparison. It is defined in the Object
class, where it behaves exactly like the ==
operator. However, many classes (like String
, Integer
, etc.) override the .equals()
method to provide a meaningful comparison of the object's actual contents rather than their memory location.Example:
String s1 = new String("HELLO");
String s2 = new String("HELLO");
String s3 = s1;
System.out.println(s1 == s2);
// false - they are two different objects in memory
System.out.println(s1.equals(s2));
// true - their content is the same
System.out.println(s1 == s3);
// true - both references point to the same object
It is a best practice to always override both .equals()
and .hashCode()
if you plan to use your custom objects in collections.